Sync from Piper @429333699
PROTOBUF_SYNC_PIPER
diff --git a/python/google/protobuf/__init__.py b/python/google/protobuf/__init__.py
index b8122e8..9319c67 100644
--- a/python/google/protobuf/__init__.py
+++ b/python/google/protobuf/__init__.py
@@ -30,4 +30,4 @@
# Copyright 2007 Google Inc. All Rights Reserved.
-__version__ = '3.18.1'
+__version__ = '3.19.4'
diff --git a/python/google/protobuf/descriptor.py b/python/google/protobuf/descriptor.py
index 9615a58..ad70be9 100644
--- a/python/google/protobuf/descriptor.py
+++ b/python/google/protobuf/descriptor.py
@@ -667,7 +667,7 @@
full_name (str): Full name of the type, including package name
and any enclosing type(s).
- values (list[EnumValueDescriptors]): List of the values
+ values (list[EnumValueDescriptor]): List of the values
in this enum.
values_by_name (dict(str, EnumValueDescriptor)): Same as :attr:`values`,
but indexed by the "name" field of each EnumValueDescriptor.
diff --git a/python/google/protobuf/internal/_parameterized.py b/python/google/protobuf/internal/_parameterized.py
index 6b6ba65..afdbb78 100755
--- a/python/google/protobuf/internal/_parameterized.py
+++ b/python/google/protobuf/internal/_parameterized.py
@@ -148,10 +148,7 @@
import functools
import re
import types
-try:
- import unittest2 as unittest
-except ImportError:
- import unittest
+import unittest
import uuid
try:
diff --git a/python/google/protobuf/internal/api_implementation.cc b/python/google/protobuf/internal/api_implementation.cc
index 241942e..33f5b04 100644
--- a/python/google/protobuf/internal/api_implementation.cc
+++ b/python/google/protobuf/internal/api_implementation.cc
@@ -28,6 +28,7 @@
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
namespace google {
diff --git a/python/google/protobuf/internal/descriptor_database_test.py b/python/google/protobuf/internal/descriptor_database_test.py
index ad3ca64..3c086b9 100644
--- a/python/google/protobuf/internal/descriptor_database_test.py
+++ b/python/google/protobuf/internal/descriptor_database_test.py
@@ -100,7 +100,7 @@
self.assertEqual(file_desc_proto2, db.FindFileContainingSymbol(
'protobuf_unittest.TestAllTypes.none_field'))
- with self.assertRaisesRegexp(KeyError, r'\'protobuf_unittest\.NoneMessage\''):
+ with self.assertRaisesRegex(KeyError, r'\'protobuf_unittest\.NoneMessage\''):
db.FindFileContainingSymbol('protobuf_unittest.NoneMessage')
def testConflictRegister(self):
diff --git a/python/google/protobuf/internal/descriptor_pool_test.py b/python/google/protobuf/internal/descriptor_pool_test.py
index 501c9a6..61cec3f 100644
--- a/python/google/protobuf/internal/descriptor_pool_test.py
+++ b/python/google/protobuf/internal/descriptor_pool_test.py
@@ -654,11 +654,11 @@
enum_value.number = 0
self.db.Add(file_proto)
- self.assertRaisesRegexp(KeyError, 'SubMessage',
- self.pool.FindMessageTypeByName,
- 'collector.ErrorMessage')
- self.assertRaisesRegexp(KeyError, 'SubMessage',
- self.pool.FindFileByName, 'error_file')
+ self.assertRaisesRegex(KeyError, 'SubMessage',
+ self.pool.FindMessageTypeByName,
+ 'collector.ErrorMessage')
+ self.assertRaisesRegex(KeyError, 'SubMessage', self.pool.FindFileByName,
+ 'error_file')
with self.assertRaises(KeyError) as exc:
self.pool.FindFileByName('none_file')
self.assertIn(str(exc.exception), ('\'none_file\'',
diff --git a/python/google/protobuf/internal/enum_type_wrapper.py b/python/google/protobuf/internal/enum_type_wrapper.py
index 9a53999..65d2c7a 100644
--- a/python/google/protobuf/internal/enum_type_wrapper.py
+++ b/python/google/protobuf/internal/enum_type_wrapper.py
@@ -43,6 +43,15 @@
DESCRIPTOR = None
+ # This is a type alias, which mypy typing stubs can type as
+ # a genericized parameter constrained to an int, allowing subclasses
+ # to be typed with more constraint in .pyi stubs
+ # Eg.
+ # def MyGeneratedEnum(Message):
+ # ValueType = NewType('ValueType', int)
+ # def Name(self, number: MyGeneratedEnum.ValueType) -> str
+ ValueType = int
+
def __init__(self, enum_type):
"""Inits EnumTypeWrapper with an EnumDescriptor."""
self._enum_type = enum_type
diff --git a/python/google/protobuf/internal/generator_test.py b/python/google/protobuf/internal/generator_test.py
index 0c4299a..9883fce 100644
--- a/python/google/protobuf/internal/generator_test.py
+++ b/python/google/protobuf/internal/generator_test.py
@@ -39,10 +39,7 @@
__author__ = 'robinson@google.com (Will Robinson)'
-try:
- import unittest2 as unittest #PY26
-except ImportError:
- import unittest
+import unittest
from google.protobuf.internal import test_bad_identifiers_pb2
from google.protobuf import unittest_custom_options_pb2
diff --git a/python/google/protobuf/internal/json_format_test.py b/python/google/protobuf/internal/json_format_test.py
index 3545563..d018c3f 100644
--- a/python/google/protobuf/internal/json_format_test.py
+++ b/python/google/protobuf/internal/json_format_test.py
@@ -100,10 +100,8 @@
def CheckError(self, text, error_message):
message = json_format_proto3_pb2.TestMessage()
- self.assertRaisesRegexp(
- json_format.ParseError,
- error_message,
- json_format.Parse, text, message)
+ self.assertRaisesRegex(json_format.ParseError, error_message,
+ json_format.Parse, text, message)
class JsonFormatTest(JsonFormatBase):
@@ -812,9 +810,8 @@
json_format.Parse('{"messageValue": {}}', parsed_message)
self.assertTrue(parsed_message.HasField('message_value'))
# Null is not allowed to be used as an element in repeated field.
- self.assertRaisesRegexp(
- json_format.ParseError,
- r'Failed to parse repeatedInt32Value field: '
+ self.assertRaisesRegex(
+ json_format.ParseError, r'Failed to parse repeatedInt32Value field: '
r'null is not allowed to be used as an element in a repeated field '
r'at TestMessage.repeatedInt32Value\[1\].', json_format.Parse,
'{"repeatedInt32Value":[1, null]}', parsed_message)
@@ -901,7 +898,7 @@
json_format.Parse(text, message)
# Proto2 does not accept unknown enums.
message = unittest_pb2.TestAllTypes()
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
'Failed to parse optionalNestedEnum field: Invalid enum value 12345 '
'for enum type protobuf_unittest.TestAllTypes.NestedEnum at '
@@ -1019,28 +1016,25 @@
def testInvalidMap(self):
message = json_format_proto3_pb2.TestMap()
text = '{"int32Map": {"null": 2, "2": 3}}'
- self.assertRaisesRegexp(
- json_format.ParseError,
- 'Failed to parse int32Map field: invalid literal',
- json_format.Parse, text, message)
+ self.assertRaisesRegex(json_format.ParseError,
+ 'Failed to parse int32Map field: invalid literal',
+ json_format.Parse, text, message)
text = '{"int32Map": {1: 2, "2": 3}}'
- self.assertRaisesRegexp(
- json_format.ParseError,
- (r'Failed to load JSON: Expecting property name'
- r'( enclosed in double quotes)?: line 1'),
- json_format.Parse, text, message)
+ self.assertRaisesRegex(json_format.ParseError,
+ (r'Failed to load JSON: Expecting property name'
+ r'( enclosed in double quotes)?: line 1'),
+ json_format.Parse, text, message)
text = '{"boolMap": {"null": 1}}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
'Failed to parse boolMap field: Expected "true" or "false", not null at '
'TestMap.boolMap.key', json_format.Parse, text, message)
text = r'{"stringMap": {"a": 3, "\u0061": 2}}'
- self.assertRaisesRegexp(
- json_format.ParseError,
- 'Failed to load JSON: duplicate key a',
- json_format.Parse, text, message)
+ self.assertRaisesRegex(json_format.ParseError,
+ 'Failed to load JSON: duplicate key a',
+ json_format.Parse, text, message)
text = r'{"stringMap": 0}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
'Failed to parse stringMap field: Map field string_map must be '
'in a dict which is 0 at TestMap.stringMap.', json_format.Parse, text,
@@ -1055,27 +1049,24 @@
' format \'%Y-%m-%dT%H:%M:%S\' at TestTimestamp.value.',
json_format.Parse, text, message)
text = '{"value": "1970-01-01T00:00:00.0123456789012Z"}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
- 'nanos 0123456789012 more than 9 fractional digits.',
- json_format.Parse, text, message)
+ 'nanos 0123456789012 more than 9 fractional digits.', json_format.Parse,
+ text, message)
text = '{"value": "1972-01-01T01:00:00.01+08"}'
- self.assertRaisesRegexp(
- json_format.ParseError,
- (r'Invalid timezone offset value: \+08.'),
- json_format.Parse, text, message)
+ self.assertRaisesRegex(json_format.ParseError,
+ (r'Invalid timezone offset value: \+08.'),
+ json_format.Parse, text, message)
# Time smaller than minimum time.
text = '{"value": "0000-01-01T00:00:00Z"}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
'Failed to parse value field: year (0 )?is out of range.',
json_format.Parse, text, message)
# Time bigger than maximum time.
message.value.seconds = 253402300800
- self.assertRaisesRegexp(
- OverflowError,
- 'date value out of range',
- json_format.MessageToJson, message)
+ self.assertRaisesRegex(OverflowError, 'date value out of range',
+ json_format.MessageToJson, message)
# Lower case t does not accept.
text = '{"value": "0001-01-01t00:00:00Z"}'
with self.assertRaises(json_format.ParseError) as e:
@@ -1097,11 +1088,10 @@
def testInvalidListValue(self):
message = json_format_proto3_pb2.TestListValue()
text = '{"value": 1234}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
r'Failed to parse value field: ListValue must be in \[\] which is '
- '1234 at TestListValue.value.',
- json_format.Parse, text, message)
+ '1234 at TestListValue.value.', json_format.Parse, text, message)
class UnknownClass(object):
@@ -1116,16 +1106,15 @@
def testInvalidStruct(self):
message = json_format_proto3_pb2.TestStruct()
text = '{"value": 1234}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
'Failed to parse value field: Struct must be in a dict which is '
- '1234 at TestStruct.value',
- json_format.Parse, text, message)
+ '1234 at TestStruct.value', json_format.Parse, text, message)
def testTimestampInvalidStringValue(self):
message = json_format_proto3_pb2.TestTimestamp()
text = '{"value": {"foo": 123}}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
r"Timestamp JSON value not a string: {u?'foo': 123}", json_format.Parse,
text, message)
@@ -1133,15 +1122,14 @@
def testDurationInvalidStringValue(self):
message = json_format_proto3_pb2.TestDuration()
text = '{"value": {"foo": 123}}'
- self.assertRaisesRegexp(
- json_format.ParseError,
- r"Duration JSON value not a string: {u?'foo': 123}", json_format.Parse,
- text, message)
+ self.assertRaisesRegex(json_format.ParseError,
+ r"Duration JSON value not a string: {u?'foo': 123}",
+ json_format.Parse, text, message)
def testFieldMaskInvalidStringValue(self):
message = json_format_proto3_pb2.TestFieldMask()
text = '{"value": {"foo": 123}}'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
r"FieldMask JSON value not a string: {u?'foo': 123}", json_format.Parse,
text, message)
@@ -1149,10 +1137,7 @@
def testInvalidAny(self):
message = any_pb2.Any()
text = '{"@type": "type.googleapis.com/google.protobuf.Int32Value"}'
- self.assertRaisesRegexp(
- KeyError,
- 'value',
- json_format.Parse, text, message)
+ self.assertRaisesRegex(KeyError, 'value', json_format.Parse, text, message)
text = '{"value": 1234}'
self.assertRaisesRegex(json_format.ParseError,
'@type is missing when parsing any message at Any',
@@ -1247,12 +1232,10 @@
def __repr__(self):
return 'v'
message = json_format_proto3_pb2.TestValue()
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
json_format.ParseError,
r"Value v has unexpected type <class '.*\.UnknownClass'>.",
- json_format.ParseDict,
- {'value': UnknownClass()},
- message)
+ json_format.ParseDict, {'value': UnknownClass()}, message)
def testMessageToDict(self):
message = json_format_proto3_pb2.TestMessage()
diff --git a/python/google/protobuf/internal/message_test.py b/python/google/protobuf/internal/message_test.py
index e8d86a2..a5c5a0d 100644
--- a/python/google/protobuf/internal/message_test.py
+++ b/python/google/protobuf/internal/message_test.py
@@ -75,21 +75,19 @@
UCS2_MAXUNICODE = 65535
-
warnings.simplefilter('error', DeprecationWarning)
-@_parameterized.named_parameters(
- ('_proto2', unittest_pb2),
- ('_proto3', unittest_proto3_arena_pb2))
+@_parameterized.named_parameters(('_proto2', unittest_pb2),
+ ('_proto3', unittest_proto3_arena_pb2))
@testing_refleaks.TestCase
class MessageTest(unittest.TestCase):
def testBadUtf8String(self, message_module):
if api_implementation.Type() != 'python':
- self.skipTest("Skipping testBadUtf8String, currently only the python "
- "api implementation raises UnicodeDecodeError when a "
- "string field contains bad utf-8.")
+ self.skipTest('Skipping testBadUtf8String, currently only the python '
+ 'api implementation raises UnicodeDecodeError when a '
+ 'string field contains bad utf-8.')
bad_utf8_data = test_util.GoldenFileData('bad_utf8_string')
with self.assertRaises(UnicodeDecodeError) as context:
message_module.TestAllTypes.FromString(bad_utf8_data)
@@ -100,8 +98,7 @@
# and doesn't preserve unknown fields, so for proto3 we use a golden
# message that doesn't have these fields set.
if message_module is unittest_pb2:
- golden_data = test_util.GoldenFileData(
- 'golden_message_oneof_implemented')
+ golden_data = test_util.GoldenFileData('golden_message_oneof_implemented')
else:
golden_data = test_util.GoldenFileData('golden_message_proto3')
@@ -440,8 +437,7 @@
except TypeError:
pass
self.assertEqual(2, len(msg.repeated_nested_message))
- self.assertEqual([1, 2],
- [m.bb for m in msg.repeated_nested_message])
+ self.assertEqual([1, 2], [m.bb for m in msg.repeated_nested_message])
def testInsertRepeatedCompositeField(self, message_module):
msg = message_module.TestAllTypes()
@@ -463,22 +459,22 @@
self.assertEqual(5, len(msg.repeated_nested_message))
self.assertEqual([-1000, 2, -1, 1, 3],
[m.bb for m in msg.repeated_nested_message])
- self.assertEqual(str(msg),
- 'repeated_nested_message {\n'
- ' bb: -1000\n'
- '}\n'
- 'repeated_nested_message {\n'
- ' bb: 2\n'
- '}\n'
- 'repeated_nested_message {\n'
- ' bb: -1\n'
- '}\n'
- 'repeated_nested_message {\n'
- ' bb: 1\n'
- '}\n'
- 'repeated_nested_message {\n'
- ' bb: 3\n'
- '}\n')
+ self.assertEqual(
+ str(msg), 'repeated_nested_message {\n'
+ ' bb: -1000\n'
+ '}\n'
+ 'repeated_nested_message {\n'
+ ' bb: 2\n'
+ '}\n'
+ 'repeated_nested_message {\n'
+ ' bb: -1\n'
+ '}\n'
+ 'repeated_nested_message {\n'
+ ' bb: 1\n'
+ '}\n'
+ 'repeated_nested_message {\n'
+ ' bb: 3\n'
+ '}\n')
self.assertEqual(sub_msg.bb, 1)
def testMergeFromRepeatedField(self, message_module):
@@ -497,8 +493,7 @@
self.assertEqual(4, len(msg.repeated_int32))
msg.repeated_nested_message.MergeFrom(other_msg.repeated_nested_message)
- self.assertEqual([1, 2, 3, 4],
- [m.bb for m in msg.repeated_nested_message])
+ self.assertEqual([1, 2, 3, 4], [m.bb for m in msg.repeated_nested_message])
def testAddWrongRepeatedNestedField(self, message_module):
msg = message_module.TestAllTypes()
@@ -543,8 +538,7 @@
msg.repeated_nested_message.add(bb=3)
msg.repeated_nested_message.add(bb=4)
- self.assertEqual([1, 2, 3, 4],
- [m.bb for m in msg.repeated_nested_message])
+ self.assertEqual([1, 2, 3, 4], [m.bb for m in msg.repeated_nested_message])
self.assertEqual([4, 3, 2, 1],
[m.bb for m in reversed(msg.repeated_nested_message)])
self.assertEqual([4, 3, 2, 1],
@@ -627,8 +621,9 @@
self.assertEqual(message.repeated_nested_message[3].bb, 4)
self.assertEqual(message.repeated_nested_message[4].bb, 5)
self.assertEqual(message.repeated_nested_message[5].bb, 6)
- self.assertEqual(str(message.repeated_nested_message),
- '[bb: 1\n, bb: 2\n, bb: 3\n, bb: 4\n, bb: 5\n, bb: 6\n]')
+ self.assertEqual(
+ str(message.repeated_nested_message),
+ '[bb: 1\n, bb: 2\n, bb: 3\n, bb: 4\n, bb: 5\n, bb: 6\n]')
def testSortingRepeatedCompositeFieldsStable(self, message_module):
"""Check passing a custom comparator to sort a repeated composite field."""
@@ -642,18 +637,16 @@
message.repeated_nested_message.add().bb = 24
message.repeated_nested_message.add().bb = 10
message.repeated_nested_message.sort(key=lambda z: z.bb // 10)
- self.assertEqual(
- [13, 11, 10, 21, 20, 24, 33],
- [n.bb for n in message.repeated_nested_message])
+ self.assertEqual([13, 11, 10, 21, 20, 24, 33],
+ [n.bb for n in message.repeated_nested_message])
# Make sure that for the C++ implementation, the underlying fields
# are actually reordered.
pb = message.SerializeToString()
message.Clear()
message.MergeFromString(pb)
- self.assertEqual(
- [13, 11, 10, 21, 20, 24, 33],
- [n.bb for n in message.repeated_nested_message])
+ self.assertEqual([13, 11, 10, 21, 20, 24, 33],
+ [n.bb for n in message.repeated_nested_message])
def testRepeatedCompositeFieldSortArguments(self, message_module):
"""Check sorting a repeated composite field using list.sort() arguments."""
@@ -826,7 +819,7 @@
self.assertTrue(m.HasField('oneof_uint32'))
self.assertFalse(m.HasField('oneof_string'))
- m.oneof_string = ""
+ m.oneof_string = ''
self.assertEqual('oneof_string', m.WhichOneof('oneof_field'))
self.assertTrue(m.HasField('oneof_string'))
self.assertFalse(m.HasField('oneof_uint32'))
@@ -973,7 +966,9 @@
def testAssignByteStringToUnicodeField(self, message_module):
"""Assigning a byte string to a string field should result
- in the value being converted to a Unicode string."""
+
+ in the value being converted to a Unicode string.
+ """
m = message_module.TestAllTypes()
m.optional_string = str('')
self.assertIsInstance(m.optional_string, str)
@@ -1001,8 +996,7 @@
with self.assertRaises(NameError) as _:
m.repeated_int32.extend(a for i in range(10)) # pylint: disable=undefined-variable
with self.assertRaises(NameError) as _:
- m.repeated_nested_enum.extend(
- a for i in range(10)) # pylint: disable=undefined-variable
+ m.repeated_nested_enum.extend(a for i in range(10)) # pylint: disable=undefined-variable
FALSY_VALUES = [None, False, 0, 0.0, b'', u'', bytearray(), [], {}, set()]
@@ -1179,14 +1173,12 @@
pickle.dumps(m.repeated_int32, pickle.HIGHEST_PROTOCOL)
def testSortEmptyRepeatedCompositeContainer(self, message_module):
- """Exercise a scenario that has led to segfaults in the past.
- """
+ """Exercise a scenario that has led to segfaults in the past."""
m = message_module.TestAllTypes()
m.repeated_nested_message.sort()
def testHasFieldOnRepeatedField(self, message_module):
- """Using HasField on a repeated field should raise an exception.
- """
+ """Using HasField on a repeated field should raise an exception."""
m = message_module.TestAllTypes()
with self.assertRaises(ValueError) as _:
m.HasField('repeated_int32')
@@ -1226,6 +1218,7 @@
def testReleasedNestedMessages(self, message_module):
"""A case that lead to a segfault when a message detached from its parent
+
container has itself a child container.
"""
m = message_module.NestedTestAllTypes()
@@ -1271,17 +1264,17 @@
def testFieldPresence(self):
message = unittest_pb2.TestAllTypes()
- self.assertFalse(message.HasField("optional_int32"))
- self.assertFalse(message.HasField("optional_bool"))
- self.assertFalse(message.HasField("optional_nested_message"))
+ self.assertFalse(message.HasField('optional_int32'))
+ self.assertFalse(message.HasField('optional_bool'))
+ self.assertFalse(message.HasField('optional_nested_message'))
with self.assertRaises(ValueError):
- message.HasField("field_doesnt_exist")
+ message.HasField('field_doesnt_exist')
with self.assertRaises(ValueError):
- message.HasField("repeated_int32")
+ message.HasField('repeated_int32')
with self.assertRaises(ValueError):
- message.HasField("repeated_nested_message")
+ message.HasField('repeated_nested_message')
self.assertEqual(0, message.optional_int32)
self.assertEqual(False, message.optional_bool)
@@ -1291,27 +1284,27 @@
message.optional_int32 = 0
message.optional_bool = False
message.optional_nested_message.bb = 0
- self.assertTrue(message.HasField("optional_int32"))
- self.assertTrue(message.HasField("optional_bool"))
- self.assertTrue(message.HasField("optional_nested_message"))
+ self.assertTrue(message.HasField('optional_int32'))
+ self.assertTrue(message.HasField('optional_bool'))
+ self.assertTrue(message.HasField('optional_nested_message'))
# Set the fields to non-default values.
message.optional_int32 = 5
message.optional_bool = True
message.optional_nested_message.bb = 15
- self.assertTrue(message.HasField(u"optional_int32"))
- self.assertTrue(message.HasField("optional_bool"))
- self.assertTrue(message.HasField("optional_nested_message"))
+ self.assertTrue(message.HasField(u'optional_int32'))
+ self.assertTrue(message.HasField('optional_bool'))
+ self.assertTrue(message.HasField('optional_nested_message'))
# Clearing the fields unsets them and resets their value to default.
- message.ClearField("optional_int32")
- message.ClearField(u"optional_bool")
- message.ClearField("optional_nested_message")
+ message.ClearField('optional_int32')
+ message.ClearField(u'optional_bool')
+ message.ClearField('optional_nested_message')
- self.assertFalse(message.HasField("optional_int32"))
- self.assertFalse(message.HasField("optional_bool"))
- self.assertFalse(message.HasField("optional_nested_message"))
+ self.assertFalse(message.HasField('optional_int32'))
+ self.assertFalse(message.HasField('optional_bool'))
+ self.assertFalse(message.HasField('optional_nested_message'))
self.assertEqual(0, message.optional_int32)
self.assertEqual(False, message.optional_bool)
self.assertEqual(0, message.optional_nested_message.bb)
@@ -1361,16 +1354,17 @@
msg1 = more_extensions_pb2.TopLevelMessage()
msg2 = more_extensions_pb2.TopLevelMessage()
# Cpp extension will lazily create a sub message which is immutable.
- self.assertEqual(0, msg1.submessage.Extensions[
- more_extensions_pb2.optional_int_extension])
+ self.assertEqual(
+ 0,
+ msg1.submessage.Extensions[more_extensions_pb2.optional_int_extension])
self.assertFalse(msg1.HasField('submessage'))
- msg2.submessage.Extensions[
- more_extensions_pb2.optional_int_extension] = 123
+ msg2.submessage.Extensions[more_extensions_pb2.optional_int_extension] = 123
# Make sure cmessage and extensions pointing to a mutable message
# after merge instead of the lazily created message.
msg1.MergeFrom(msg2)
- self.assertEqual(123, msg1.submessage.Extensions[
- more_extensions_pb2.optional_int_extension])
+ self.assertEqual(
+ 123,
+ msg1.submessage.Extensions[more_extensions_pb2.optional_int_extension])
def testGoldenExtensions(self):
golden_data = test_util.GoldenFileData('golden_message')
@@ -1404,17 +1398,19 @@
# This is still an incomplete proto - so serializing should fail
self.assertRaises(message.EncodeError, unpickled_message.SerializeToString)
-
# TODO(haberman): this isn't really a proto2-specific test except that this
# message has a required field in it. Should probably be factored out so
# that we can test the other parts with proto3.
def testParsingMerge(self):
"""Check the merge behavior when a required or optional field appears
- multiple times in the input."""
+
+ multiple times in the input.
+ """
messages = [
unittest_pb2.TestAllTypes(),
unittest_pb2.TestAllTypes(),
- unittest_pb2.TestAllTypes() ]
+ unittest_pb2.TestAllTypes()
+ ]
messages[0].optional_int32 = 1
messages[1].optional_int64 = 2
messages[2].optional_int32 = 3
@@ -1447,15 +1443,16 @@
self.assertEqual(parsing_merge.optional_all_types, merged_message)
self.assertEqual(parsing_merge.optionalgroup.optional_group_all_types,
merged_message)
- self.assertEqual(parsing_merge.Extensions[
- unittest_pb2.TestParsingMerge.optional_ext],
- merged_message)
+ self.assertEqual(
+ parsing_merge.Extensions[unittest_pb2.TestParsingMerge.optional_ext],
+ merged_message)
# Repeated fields should not be merged.
self.assertEqual(len(parsing_merge.repeated_all_types), 3)
self.assertEqual(len(parsing_merge.repeatedgroup), 3)
- self.assertEqual(len(parsing_merge.Extensions[
- unittest_pb2.TestParsingMerge.repeated_ext]), 3)
+ self.assertEqual(
+ len(parsing_merge.Extensions[
+ unittest_pb2.TestParsingMerge.repeated_ext]), 3)
def testPythonicInit(self):
message = unittest_pb2.TestAllTypes(
@@ -1467,8 +1464,11 @@
optional_nested_message={'bb': 500},
optional_foreign_message={},
optional_nested_enum='BAZ',
- repeatedgroup=[{'a': 600},
- {'a': 700}],
+ repeatedgroup=[{
+ 'a': 600
+ }, {
+ 'a': 700
+ }],
repeated_nested_enum=['FOO', unittest_pb2.TestAllTypes.BAR],
default_int32=800,
oneof_string='y')
@@ -1848,8 +1848,7 @@
self.assertEqual(True, msg2.map_bool_bool[True])
self.assertEqual(2, msg2.map_int32_enum[888])
self.assertEqual(456, msg2.map_int32_enum[123])
- self.assertEqual('{-123: -456}',
- str(msg2.map_int32_int32))
+ self.assertEqual('{-123: -456}', str(msg2.map_int32_int32))
def testMapEntryAlwaysSerialized(self):
msg = map_unittest_pb2.TestMap()
@@ -1912,8 +1911,9 @@
self.assertEqual(2, len(msg2.map_int32_foreign_message))
msg2.map_int32_foreign_message[123].c = 1
# TODO(jieluo): Fix text format for message map.
- self.assertIn(str(msg2.map_int32_foreign_message),
- ('{-456: , 123: c: 1\n}', '{123: c: 1\n, -456: }'))
+ self.assertIn(
+ str(msg2.map_int32_foreign_message),
+ ('{-456: , 123: c: 1\n}', '{123: c: 1\n, -456: }'))
def testNestedMessageMapItemDelete(self):
msg = map_unittest_pb2.TestMap()
@@ -2041,8 +2041,7 @@
# Test when cpp extension cache a map.
m1 = map_unittest_pb2.TestMap()
m2 = map_unittest_pb2.TestMap()
- self.assertEqual(m1.map_int32_foreign_message,
- m1.map_int32_foreign_message)
+ self.assertEqual(m1.map_int32_foreign_message, m1.map_int32_foreign_message)
m2.map_int32_foreign_message[123].c = 10
m1.MergeFrom(m2)
self.assertEqual(10, m2.map_int32_foreign_message[123].c)
@@ -2070,7 +2069,7 @@
def testMergeFromBadType(self):
msg = map_unittest_pb2.TestMap()
- with self.assertRaisesRegexp(
+ with self.assertRaisesRegex(
TypeError,
r'Parameter to MergeFrom\(\) must be instance of same class: expected '
r'.+TestMap got int\.'):
@@ -2078,7 +2077,7 @@
def testCopyFromBadType(self):
msg = map_unittest_pb2.TestMap()
- with self.assertRaisesRegexp(
+ with self.assertRaisesRegex(
TypeError,
r'Parameter to [A-Za-z]*From\(\) must be instance of same class: '
r'expected .+TestMap got int\.'):
@@ -2167,6 +2166,34 @@
for key in int32_foreign_iter:
pass
+ def testModifyMapEntryWhileIterating(self):
+ msg = map_unittest_pb2.TestMap()
+
+ msg.map_string_string['abc'] = '123'
+ msg.map_string_string['def'] = '456'
+ msg.map_string_string['ghi'] = '789'
+
+ msg.map_int32_foreign_message[5].c = 5
+ msg.map_int32_foreign_message[6].c = 6
+ msg.map_int32_foreign_message[7].c = 7
+
+ string_string_keys = list(msg.map_string_string.keys())
+ int32_foreign_keys = list(msg.map_int32_foreign_message.keys())
+
+ keys = []
+ for key in msg.map_string_string:
+ keys.append(key)
+ msg.map_string_string[key] = '000'
+ self.assertEqual(keys, string_string_keys)
+ self.assertEqual(keys, list(msg.map_string_string.keys()))
+
+ keys = []
+ for key in msg.map_int32_foreign_message:
+ keys.append(key)
+ msg.map_int32_foreign_message[key].c = 0
+ self.assertEqual(keys, int32_foreign_keys)
+ self.assertEqual(keys, list(msg.map_int32_foreign_message.keys()))
+
def testSubmessageMap(self):
msg = map_unittest_pb2.TestMap()
@@ -2278,7 +2305,7 @@
msg1 = map_unittest_pb2.TestMap()
msg1.map_string_foreign_message['test'].c = 42
msg2 = map_unittest_pb2.TestMap(
- map_string_foreign_message=msg1.map_string_foreign_message)
+ map_string_foreign_message=msg1.map_string_foreign_message)
self.assertEqual(42, msg2.map_string_foreign_message['test'].c)
def testMapFieldRaisesCorrectError(self):
@@ -2413,24 +2440,21 @@
msg2.MergeFromString(serialized)
self.assertEqual(msg2.optional_string, u'😍')
- msg = unittest_proto3_arena_pb2.TestAllTypes(
- optional_string=u'\ud001')
+ msg = unittest_proto3_arena_pb2.TestAllTypes(optional_string=u'\ud001')
self.assertEqual(msg.optional_string, u'\ud001')
def testSurrogatesInPython3(self):
# Surrogates are rejected at setters in Python3.
with self.assertRaises(ValueError):
- unittest_proto3_arena_pb2.TestAllTypes(
- optional_string=u'\ud801\udc01')
+ unittest_proto3_arena_pb2.TestAllTypes(optional_string=u'\ud801\udc01')
with self.assertRaises(ValueError):
- unittest_proto3_arena_pb2.TestAllTypes(
- optional_string=b'\xed\xa0\x81')
+ unittest_proto3_arena_pb2.TestAllTypes(optional_string=b'\xed\xa0\x81')
with self.assertRaises(ValueError):
- unittest_proto3_arena_pb2.TestAllTypes(
- optional_string=u'\ud801')
+ unittest_proto3_arena_pb2.TestAllTypes(optional_string=u'\ud801')
with self.assertRaises(ValueError):
- unittest_proto3_arena_pb2.TestAllTypes(
- optional_string=u'\ud801\ud801')
+ unittest_proto3_arena_pb2.TestAllTypes(optional_string=u'\ud801\ud801')
+
+
@testing_refleaks.TestCase
@@ -2441,8 +2465,9 @@
tp_name = str(type(msg)).split("'")[1]
valid_names = ('Repeated%sContainer' % base_name,
'Repeated%sFieldContainer' % base_name)
- self.assertTrue(any(tp_name.endswith(v) for v in valid_names),
- '%r does end with any of %r' % (tp_name, valid_names))
+ self.assertTrue(
+ any(tp_name.endswith(v) for v in valid_names),
+ '%r does end with any of %r' % (tp_name, valid_names))
parts = tp_name.split('.')
class_name = parts[-1]
@@ -2455,6 +2480,7 @@
self.assertImportFromName(pb.repeated_int32, 'Scalar')
self.assertImportFromName(pb.repeated_nested_message, 'Composite')
+
@testing_refleaks.TestCase
class PackedFieldTest(unittest.TestCase):
@@ -2574,5 +2600,6 @@
q.ParseFromString(self.p_serialized)
self.assertEqual(self.p.field.payload, q.field.payload)
+
if __name__ == '__main__':
unittest.main()
diff --git a/python/google/protobuf/internal/proto_builder_test.py b/python/google/protobuf/internal/proto_builder_test.py
index 8e2afaf..48077b0 100644
--- a/python/google/protobuf/internal/proto_builder_test.py
+++ b/python/google/protobuf/internal/proto_builder_test.py
@@ -31,10 +31,7 @@
"""Tests for google.protobuf.proto_builder."""
import collections
-try:
- import unittest2 as unittest
-except ImportError:
- import unittest
+import unittest
from google.protobuf import descriptor_pb2 # pylint: disable=g-import-not-at-top
from google.protobuf import descriptor
diff --git a/python/google/protobuf/internal/reflection_test.py b/python/google/protobuf/internal/reflection_test.py
index 9343389..66dd0c7 100644
--- a/python/google/protobuf/internal/reflection_test.py
+++ b/python/google/protobuf/internal/reflection_test.py
@@ -37,6 +37,7 @@
import gc
import operator
import struct
+import sys
import warnings
import unittest
@@ -376,7 +377,8 @@
self.assertRaises(TypeError, setattr, proto, 'optional_float', 'foo')
self.assertRaises(TypeError, setattr, proto, 'optional_double', 'foo')
# TODO(jieluo): Fix type checking difference for python and c extension
- if api_implementation.Type() == 'python':
+ if (api_implementation.Type() == 'python' or
+ (sys.version_info.major, sys.version_info.minor) >= (3, 10)):
self.assertRaises(TypeError, setattr, proto, 'optional_bool', 1.1)
else:
proto.optional_bool = 1.1
@@ -427,7 +429,7 @@
pb.optional_uint64 = '2'
# The exact error should propagate with a poorly written custom integer.
- with self.assertRaisesRegexp(RuntimeError, 'my_error'):
+ with self.assertRaisesRegex(RuntimeError, 'my_error'):
pb.optional_uint64 = test_util.NonStandardInteger(5, 'my_error')
def assetIntegerBoundsChecking(self, integer_fn, message_module):
diff --git a/python/google/protobuf/internal/well_known_types_test.py b/python/google/protobuf/internal/well_known_types_test.py
index 37aec7e..3912901 100644
--- a/python/google/protobuf/internal/well_known_types_test.py
+++ b/python/google/protobuf/internal/well_known_types_test.py
@@ -36,8 +36,6 @@
import datetime
import unittest
-import dateutil.tz
-
from google.protobuf import any_pb2
from google.protobuf import duration_pb2
from google.protobuf import field_mask_pb2
@@ -50,9 +48,17 @@
from google.protobuf.internal import well_known_types
from google.protobuf import descriptor
from google.protobuf import text_format
-from google3.pyglib import datelib
from google.protobuf.internal import _parameterized
+try:
+ # New module in Python 3.9:
+ import zoneinfo # pylint:disable=g-import-not-at-top
+ _TZ_JAPAN = zoneinfo.ZoneInfo('Japan')
+ _TZ_PACIFIC = zoneinfo.ZoneInfo('US/Pacific')
+except ImportError:
+ _TZ_JAPAN = datetime.timezone(datetime.timedelta(hours=9), 'Japan')
+ _TZ_PACIFIC = datetime.timezone(datetime.timedelta(hours=-8), 'US/Pacific')
+
class TimeUtilTestBase(_parameterized.TestCase):
@@ -270,12 +276,12 @@
# Two hours after the Unix Epoch, around the world.
@_parameterized.named_parameters(
- ('London', [1970, 1, 1, 2], dateutil.tz.UTC),
- ('Tokyo', [1970, 1, 1, 11], dateutil.tz.gettz('Japan')),
- ('LA', [1969, 12, 31, 18], dateutil.tz.gettz('US/Pacific')),
+ ('London', [1970, 1, 1, 2], datetime.timezone.utc),
+ ('Tokyo', [1970, 1, 1, 11], _TZ_JAPAN),
+ ('LA', [1969, 12, 31, 18], _TZ_PACIFIC),
)
def testTimezoneAwareDatetimeConversion(self, date_parts, tzinfo):
- original_datetime = datelib.CreateDatetime(*date_parts, tzinfo=tzinfo)
+ original_datetime = datetime.datetime(*date_parts, tzinfo=tzinfo) # pylint:disable=g-tzinfo-datetime
message = timestamp_pb2.Timestamp()
message.FromDatetime(original_datetime)
@@ -296,7 +302,7 @@
aware_datetime = message.ToDatetime(tzinfo=tzinfo)
self.assertEqual(original_datetime, aware_datetime)
self.assertEqual(
- datelib.CreateDatetime(1970, 1, 1, 2, tzinfo=dateutil.tz.UTC),
+ datetime.datetime(1970, 1, 1, 2, tzinfo=datetime.timezone.utc),
aware_datetime)
self.assertEqual(tzinfo, aware_datetime.tzinfo)
@@ -324,85 +330,64 @@
def testInvalidTimestamp(self):
message = timestamp_pb2.Timestamp()
- self.assertRaisesRegexp(
- ValueError,
- 'Failed to parse timestamp: missing valid timezone offset.',
- message.FromJsonString,
- '')
- self.assertRaisesRegexp(
- ValueError,
- 'Failed to parse timestamp: invalid trailing data '
- '1970-01-01T00:00:01Ztrail.',
- message.FromJsonString,
+ self.assertRaisesRegex(
+ ValueError, 'Failed to parse timestamp: missing valid timezone offset.',
+ message.FromJsonString, '')
+ self.assertRaisesRegex(
+ ValueError, 'Failed to parse timestamp: invalid trailing data '
+ '1970-01-01T00:00:01Ztrail.', message.FromJsonString,
'1970-01-01T00:00:01Ztrail')
- self.assertRaisesRegexp(
- ValueError,
- 'time data \'10000-01-01T00:00:00\' does not match'
- ' format \'%Y-%m-%dT%H:%M:%S\'',
- message.FromJsonString, '10000-01-01T00:00:00.00Z')
- self.assertRaisesRegexp(
- ValueError,
- 'nanos 0123456789012 more than 9 fractional digits.',
- message.FromJsonString,
- '1970-01-01T00:00:00.0123456789012Z')
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
+ ValueError, 'time data \'10000-01-01T00:00:00\' does not match'
+ ' format \'%Y-%m-%dT%H:%M:%S\'', message.FromJsonString,
+ '10000-01-01T00:00:00.00Z')
+ self.assertRaisesRegex(
+ ValueError, 'nanos 0123456789012 more than 9 fractional digits.',
+ message.FromJsonString, '1970-01-01T00:00:00.0123456789012Z')
+ self.assertRaisesRegex(
ValueError,
(r'Invalid timezone offset value: \+08.'),
message.FromJsonString,
- '1972-01-01T01:00:00.01+08',)
- self.assertRaisesRegexp(
- ValueError,
- 'year (0 )?is out of range',
- message.FromJsonString,
- '0000-01-01T00:00:00Z')
+ '1972-01-01T01:00:00.01+08',
+ )
+ self.assertRaisesRegex(ValueError, 'year (0 )?is out of range',
+ message.FromJsonString, '0000-01-01T00:00:00Z')
message.seconds = 253402300800
- self.assertRaisesRegexp(
- OverflowError,
- 'date value out of range',
- message.ToJsonString)
+ self.assertRaisesRegex(OverflowError, 'date value out of range',
+ message.ToJsonString)
def testInvalidDuration(self):
message = duration_pb2.Duration()
- self.assertRaisesRegexp(
- ValueError,
- 'Duration must end with letter "s": 1.',
- message.FromJsonString, '1')
- self.assertRaisesRegexp(
- ValueError,
- 'Couldn\'t parse duration: 1...2s.',
- message.FromJsonString, '1...2s')
+ self.assertRaisesRegex(ValueError, 'Duration must end with letter "s": 1.',
+ message.FromJsonString, '1')
+ self.assertRaisesRegex(ValueError, 'Couldn\'t parse duration: 1...2s.',
+ message.FromJsonString, '1...2s')
text = '-315576000001.000000000s'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
r'Duration is not valid\: Seconds -315576000001 must be in range'
- r' \[-315576000000\, 315576000000\].',
- message.FromJsonString, text)
+ r' \[-315576000000\, 315576000000\].', message.FromJsonString, text)
text = '315576000001.000000000s'
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
r'Duration is not valid\: Seconds 315576000001 must be in range'
- r' \[-315576000000\, 315576000000\].',
- message.FromJsonString, text)
+ r' \[-315576000000\, 315576000000\].', message.FromJsonString, text)
message.seconds = -315576000001
message.nanos = 0
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
r'Duration is not valid\: Seconds -315576000001 must be in range'
- r' \[-315576000000\, 315576000000\].',
- message.ToJsonString)
+ r' \[-315576000000\, 315576000000\].', message.ToJsonString)
message.seconds = 0
message.nanos = 999999999 + 1
- self.assertRaisesRegexp(
- ValueError,
- r'Duration is not valid\: Nanos 1000000000 must be in range'
- r' \[-999999999\, 999999999\].',
- message.ToJsonString)
+ self.assertRaisesRegex(
+ ValueError, r'Duration is not valid\: Nanos 1000000000 must be in range'
+ r' \[-999999999\, 999999999\].', message.ToJsonString)
message.seconds = -1
message.nanos = 1
- self.assertRaisesRegexp(
- ValueError,
- r'Duration is not valid\: Sign mismatch.',
- message.ToJsonString)
+ self.assertRaisesRegex(ValueError,
+ r'Duration is not valid\: Sign mismatch.',
+ message.ToJsonString)
class FieldMaskTest(unittest.TestCase):
@@ -724,34 +709,29 @@
well_known_types._SnakeCaseToCamelCase('foo3_bar'))
# No uppercase letter is allowed.
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
'Fail to print FieldMask to Json string: Path name Foo must '
'not contain uppercase letters.',
- well_known_types._SnakeCaseToCamelCase,
- 'Foo')
+ well_known_types._SnakeCaseToCamelCase, 'Foo')
# Any character after a "_" must be a lowercase letter.
# 1. "_" cannot be followed by another "_".
# 2. "_" cannot be followed by a digit.
# 3. "_" cannot appear as the last character.
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
'Fail to print FieldMask to Json string: The character after a '
'"_" must be a lowercase letter in path name foo__bar.',
- well_known_types._SnakeCaseToCamelCase,
- 'foo__bar')
- self.assertRaisesRegexp(
+ well_known_types._SnakeCaseToCamelCase, 'foo__bar')
+ self.assertRaisesRegex(
ValueError,
'Fail to print FieldMask to Json string: The character after a '
'"_" must be a lowercase letter in path name foo_3bar.',
- well_known_types._SnakeCaseToCamelCase,
- 'foo_3bar')
- self.assertRaisesRegexp(
+ well_known_types._SnakeCaseToCamelCase, 'foo_3bar')
+ self.assertRaisesRegex(
ValueError,
'Fail to print FieldMask to Json string: Trailing "_" in path '
- 'name foo_bar_.',
- well_known_types._SnakeCaseToCamelCase,
- 'foo_bar_')
+ 'name foo_bar_.', well_known_types._SnakeCaseToCamelCase, 'foo_bar_')
def testCamelCaseToSnakeCase(self):
self.assertEqual('foo_bar',
@@ -760,11 +740,10 @@
well_known_types._CamelCaseToSnakeCase('FooBar'))
self.assertEqual('foo3_bar',
well_known_types._CamelCaseToSnakeCase('foo3Bar'))
- self.assertRaisesRegexp(
+ self.assertRaisesRegex(
ValueError,
'Fail to parse FieldMask: Path name foo_bar must not contain "_"s.',
- well_known_types._CamelCaseToSnakeCase,
- 'foo_bar')
+ well_known_types._CamelCaseToSnakeCase, 'foo_bar')
class StructTest(unittest.TestCase):
diff --git a/python/google/protobuf/message.py b/python/google/protobuf/message.py
index ee46d0e..76c6802 100644
--- a/python/google/protobuf/message.py
+++ b/python/google/protobuf/message.py
@@ -194,6 +194,9 @@
"""Parse serialized protocol buffer data into this message.
Like :func:`MergeFromString()`, except we clear the object first.
+
+ Raises:
+ message.DecodeError if the input cannot be parsed.
"""
self.Clear()
return self.MergeFromString(serialized)
diff --git a/python/google/protobuf/proto_api.h b/python/google/protobuf/proto_api.h
index 2e2156a..9969a91 100644
--- a/python/google/protobuf/proto_api.h
+++ b/python/google/protobuf/proto_api.h
@@ -45,6 +45,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_PROTO_API_H__
#define GOOGLE_PROTOBUF_PYTHON_PROTO_API_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/descriptor_database.h>
diff --git a/python/google/protobuf/pyext/descriptor.cc b/python/google/protobuf/pyext/descriptor.cc
index cbf6887..1625312 100644
--- a/python/google/protobuf/pyext/descriptor.cc
+++ b/python/google/protobuf/pyext/descriptor.cc
@@ -32,6 +32,7 @@
#include <google/protobuf/pyext/descriptor.h>
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <frameobject.h>
@@ -415,11 +416,15 @@
PyTypeObject PyBaseDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".DescriptorBase", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- (destructor)Dealloc, // tp_dealloc
- 0, // tp_print
+ ".DescriptorBase", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)Dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -685,11 +690,15 @@
PyTypeObject PyMessageDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".MessageDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".MessageDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1011,11 +1020,15 @@
PyTypeObject PyFieldDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".FieldDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".FieldDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1167,11 +1180,15 @@
PyTypeObject PyEnumDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".EnumDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".EnumDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1288,11 +1305,15 @@
PyTypeObject PyEnumValueDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".EnumValueDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".EnumValueDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1477,40 +1498,44 @@
sizeof(PyFileDescriptor), // tp_basicsize
0, // tp_itemsize
(destructor)file_descriptor::Dealloc, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- nullptr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- nullptr, // tp_hash
- nullptr, // tp_call
- nullptr, // tp_str
- nullptr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
- Py_TPFLAGS_DEFAULT, // tp_flags
- "A File Descriptor", // tp_doc
- nullptr, // tp_traverse
- nullptr, // tp_clear
- nullptr, // tp_richcompare
- 0, // tp_weaklistoffset
- nullptr, // tp_iter
- nullptr, // tp_iternext
- file_descriptor::Methods, // tp_methods
- nullptr, // tp_members
- file_descriptor::Getters, // tp_getset
- &descriptor::PyBaseDescriptor_Type, // tp_base
- nullptr, // tp_dict
- nullptr, // tp_descr_get
- nullptr, // tp_descr_set
- 0, // tp_dictoffset
- nullptr, // tp_init
- nullptr, // tp_alloc
- nullptr, // tp_new
- PyObject_GC_Del, // tp_free
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ nullptr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ nullptr, // tp_hash
+ nullptr, // tp_call
+ nullptr, // tp_str
+ nullptr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A File Descriptor", // tp_doc
+ nullptr, // tp_traverse
+ nullptr, // tp_clear
+ nullptr, // tp_richcompare
+ 0, // tp_weaklistoffset
+ nullptr, // tp_iter
+ nullptr, // tp_iternext
+ file_descriptor::Methods, // tp_methods
+ nullptr, // tp_members
+ file_descriptor::Getters, // tp_getset
+ &descriptor::PyBaseDescriptor_Type, // tp_base
+ nullptr, // tp_dict
+ nullptr, // tp_descr_get
+ nullptr, // tp_descr_set
+ 0, // tp_dictoffset
+ nullptr, // tp_init
+ nullptr, // tp_alloc
+ nullptr, // tp_new
+ PyObject_GC_Del, // tp_free
};
PyObject* PyFileDescriptor_FromDescriptor(
@@ -1634,11 +1659,15 @@
PyTypeObject PyOneofDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".OneofDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".OneofDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1752,11 +1781,15 @@
PyTypeObject PyServiceDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".ServiceDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".ServiceDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1876,11 +1909,15 @@
PyTypeObject PyMethodDescriptor_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".MethodDescriptor", // tp_name
- sizeof(PyBaseDescriptor), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ ".MethodDescriptor", // tp_name
+ sizeof(PyBaseDescriptor), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
diff --git a/python/google/protobuf/pyext/descriptor.h b/python/google/protobuf/pyext/descriptor.h
index b99209d..d97e2f8 100644
--- a/python/google/protobuf/pyext/descriptor.h
+++ b/python/google/protobuf/pyext/descriptor.h
@@ -33,6 +33,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/descriptor.h>
diff --git a/python/google/protobuf/pyext/descriptor_containers.cc b/python/google/protobuf/pyext/descriptor_containers.cc
index adb1690..a87155b 100644
--- a/python/google/protobuf/pyext/descriptor_containers.cc
+++ b/python/google/protobuf/pyext/descriptor_containers.cc
@@ -49,6 +49,7 @@
// because the Python API is based on C, and does not play well with C++
// inheritance.
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/descriptor.h>
@@ -549,12 +550,16 @@
sizeof(PyContainer), // tp_basicsize
0, // tp_itemsize
nullptr, // tp_dealloc
- 0, // tp_pkrint
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- (reprfunc)ContainerRepr, // tp_repr
- nullptr, // tp_as_number
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ (reprfunc)ContainerRepr, // tp_repr
+ nullptr, // tp_as_number
&MappingSequenceMethods, // tp_as_sequence
&MappingMappingMethods, // tp_as_mapping
nullptr, // tp_hash
@@ -729,10 +734,14 @@
PyTypeObject DescriptorSequence_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) "DescriptorSequence", // tp_name
- sizeof(PyContainer), // tp_basicsize
- 0, // tp_itemsize
- nullptr, // tp_dealloc
- 0, // tp_print
+ sizeof(PyContainer), // tp_basicsize
+ 0, // tp_itemsize
+ nullptr, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -874,25 +883,29 @@
sizeof(PyContainerIterator), // tp_basicsize
0, // tp_itemsize
(destructor)Iterator_Dealloc, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- nullptr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- nullptr, // tp_hash
- nullptr, // tp_call
- nullptr, // tp_str
- nullptr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
- Py_TPFLAGS_DEFAULT, // tp_flags
- nullptr, // tp_doc
- nullptr, // tp_traverse
- nullptr, // tp_clear
- nullptr, // tp_richcompare
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ nullptr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ nullptr, // tp_hash
+ nullptr, // tp_call
+ nullptr, // tp_str
+ nullptr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ nullptr, // tp_doc
+ nullptr, // tp_traverse
+ nullptr, // tp_clear
+ nullptr, // tp_richcompare
0, // tp_weaklistoffset
PyObject_SelfIter, // tp_iter
(iternextfunc)Iterator_Next, // tp_iternext
diff --git a/python/google/protobuf/pyext/descriptor_containers.h b/python/google/protobuf/pyext/descriptor_containers.h
index 4e05c58..cf2cf4a 100644
--- a/python/google/protobuf/pyext/descriptor_containers.h
+++ b/python/google/protobuf/pyext/descriptor_containers.h
@@ -34,6 +34,7 @@
// Mappings and Sequences of descriptors.
// They implement containers like fields_by_name, EnumDescriptor.values...
// See descriptor_containers.cc for more description.
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
namespace google {
diff --git a/python/google/protobuf/pyext/descriptor_database.h b/python/google/protobuf/pyext/descriptor_database.h
index d1bd7a3..5621a22 100644
--- a/python/google/protobuf/pyext/descriptor_database.h
+++ b/python/google/protobuf/pyext/descriptor_database.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_DATABASE_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_DATABASE_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/descriptor_database.h>
diff --git a/python/google/protobuf/pyext/descriptor_pool.cc b/python/google/protobuf/pyext/descriptor_pool.cc
index 5b0ceeb..2f39281 100644
--- a/python/google/protobuf/pyext/descriptor_pool.cc
+++ b/python/google/protobuf/pyext/descriptor_pool.cc
@@ -32,6 +32,7 @@
#include <unordered_map>
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/descriptor.pb.h>
@@ -689,11 +690,15 @@
PyTypeObject PyDescriptorPool_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".DescriptorPool", // tp_name
- sizeof(PyDescriptorPool), // tp_basicsize
- 0, // tp_itemsize
- cdescriptor_pool::Dealloc, // tp_dealloc
- 0, // tp_print
+ ".DescriptorPool", // tp_name
+ sizeof(PyDescriptorPool), // tp_basicsize
+ 0, // tp_itemsize
+ cdescriptor_pool::Dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
diff --git a/python/google/protobuf/pyext/descriptor_pool.h b/python/google/protobuf/pyext/descriptor_pool.h
index 48658d3..5d3c3a9 100644
--- a/python/google/protobuf/pyext/descriptor_pool.h
+++ b/python/google/protobuf/pyext/descriptor_pool.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_POOL_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_DESCRIPTOR_POOL_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <unordered_map>
diff --git a/python/google/protobuf/pyext/extension_dict.cc b/python/google/protobuf/pyext/extension_dict.cc
index 760fc91..692029f 100644
--- a/python/google/protobuf/pyext/extension_dict.cc
+++ b/python/google/protobuf/pyext/extension_dict.cc
@@ -367,12 +367,16 @@
} // namespace extension_dict
PyTypeObject ExtensionDict_Type = {
- PyVarObject_HEAD_INIT(&PyType_Type, 0) //
- FULL_MODULE_NAME ".ExtensionDict", // tp_name
- sizeof(ExtensionDict), // tp_basicsize
- 0, // tp_itemsize
- (destructor)extension_dict::dealloc, // tp_dealloc
- 0, // tp_print
+ PyVarObject_HEAD_INIT(&PyType_Type, 0) //
+ FULL_MODULE_NAME ".ExtensionDict", // tp_name
+ sizeof(ExtensionDict), // tp_basicsize
+ 0, // tp_itemsize
+ (destructor)extension_dict::dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -439,37 +443,41 @@
sizeof(extension_dict::ExtensionIterator), // tp_basicsize
0, // tp_itemsize
extension_dict::DeallocExtensionIterator, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- nullptr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- nullptr, // tp_hash
- nullptr, // tp_call
- nullptr, // tp_str
- nullptr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
- Py_TPFLAGS_DEFAULT, // tp_flags
- "A scalar map iterator", // tp_doc
- nullptr, // tp_traverse
- nullptr, // tp_clear
- nullptr, // tp_richcompare
- 0, // tp_weaklistoffset
- PyObject_SelfIter, // tp_iter
- IterNext, // tp_iternext
- nullptr, // tp_methods
- nullptr, // tp_members
- nullptr, // tp_getset
- nullptr, // tp_base
- nullptr, // tp_dict
- nullptr, // tp_descr_get
- nullptr, // tp_descr_set
- 0, // tp_dictoffset
- nullptr, // tp_init
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ nullptr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ nullptr, // tp_hash
+ nullptr, // tp_call
+ nullptr, // tp_str
+ nullptr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "A scalar map iterator", // tp_doc
+ nullptr, // tp_traverse
+ nullptr, // tp_clear
+ nullptr, // tp_richcompare
+ 0, // tp_weaklistoffset
+ PyObject_SelfIter, // tp_iter
+ IterNext, // tp_iternext
+ nullptr, // tp_methods
+ nullptr, // tp_members
+ nullptr, // tp_getset
+ nullptr, // tp_base
+ nullptr, // tp_dict
+ nullptr, // tp_descr_get
+ nullptr, // tp_descr_set
+ 0, // tp_dictoffset
+ nullptr, // tp_init
};
} // namespace python
} // namespace protobuf
diff --git a/python/google/protobuf/pyext/extension_dict.h b/python/google/protobuf/pyext/extension_dict.h
index c9da443..a058194 100644
--- a/python/google/protobuf/pyext/extension_dict.h
+++ b/python/google/protobuf/pyext/extension_dict.h
@@ -34,6 +34,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_EXTENSION_DICT_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_EXTENSION_DICT_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <memory>
diff --git a/python/google/protobuf/pyext/field.cc b/python/google/protobuf/pyext/field.cc
index 611ac8a..0d3b0b9 100644
--- a/python/google/protobuf/pyext/field.cc
+++ b/python/google/protobuf/pyext/field.cc
@@ -87,39 +87,43 @@
sizeof(PyMessageFieldProperty), // tp_basicsize
0, // tp_itemsize
nullptr, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- (reprfunc)field::Repr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- nullptr, // tp_hash
- nullptr, // tp_call
- nullptr, // tp_str
- nullptr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
- Py_TPFLAGS_DEFAULT, // tp_flags
- "Field property of a Message", // tp_doc
- nullptr, // tp_traverse
- nullptr, // tp_clear
- nullptr, // tp_richcompare
- 0, // tp_weaklistoffset
- nullptr, // tp_iter
- nullptr, // tp_iternext
- nullptr, // tp_methods
- nullptr, // tp_members
- field::Getters, // tp_getset
- nullptr, // tp_base
- nullptr, // tp_dict
- (descrgetfunc)field::DescrGet, // tp_descr_get
- (descrsetfunc)field::DescrSet, // tp_descr_set
- 0, // tp_dictoffset
- nullptr, // tp_init
- nullptr, // tp_alloc
- nullptr, // tp_new
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ (reprfunc)field::Repr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ nullptr, // tp_hash
+ nullptr, // tp_call
+ nullptr, // tp_str
+ nullptr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
+ Py_TPFLAGS_DEFAULT, // tp_flags
+ "Field property of a Message", // tp_doc
+ nullptr, // tp_traverse
+ nullptr, // tp_clear
+ nullptr, // tp_richcompare
+ 0, // tp_weaklistoffset
+ nullptr, // tp_iter
+ nullptr, // tp_iternext
+ nullptr, // tp_methods
+ nullptr, // tp_members
+ field::Getters, // tp_getset
+ nullptr, // tp_base
+ nullptr, // tp_dict
+ (descrgetfunc)field::DescrGet, // tp_descr_get
+ (descrsetfunc)field::DescrSet, // tp_descr_set
+ 0, // tp_dictoffset
+ nullptr, // tp_init
+ nullptr, // tp_alloc
+ nullptr, // tp_new
};
PyTypeObject* CFieldProperty_Type = &_CFieldProperty_Type;
diff --git a/python/google/protobuf/pyext/field.h b/python/google/protobuf/pyext/field.h
index 7b4660c..f9f94c4 100644
--- a/python/google/protobuf/pyext/field.h
+++ b/python/google/protobuf/pyext/field.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_FIELD_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_FIELD_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
namespace google {
diff --git a/python/google/protobuf/pyext/map_container.cc b/python/google/protobuf/pyext/map_container.cc
index c953c65..4d516d2 100644
--- a/python/google/protobuf/pyext/map_container.cc
+++ b/python/google/protobuf/pyext/map_container.cc
@@ -432,12 +432,12 @@
return -1;
}
- self->version++;
-
if (v) {
// Set item to v.
- reflection->InsertOrLookupMapValue(message, self->parent_field_descriptor,
- map_key, &value);
+ if (reflection->InsertOrLookupMapValue(
+ message, self->parent_field_descriptor, map_key, &value)) {
+ self->version++;
+ }
if (!PythonToMapValueRef(self, v, reflection->SupportsUnknownEnumValues(),
&value)) {
@@ -448,6 +448,7 @@
// Delete key from map.
if (reflection->DeleteMapValue(message, self->parent_field_descriptor,
map_key)) {
+ self->version++;
return 0;
} else {
PyErr_Format(PyExc_KeyError, "Key not present in map");
@@ -853,11 +854,15 @@
PyTypeObject MapIterator_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".MapIterator", // tp_name
- sizeof(MapIterator), // tp_basicsize
- 0, // tp_itemsize
- DeallocMapIterator, // tp_dealloc
- 0, // tp_print
+ ".MapIterator", // tp_name
+ sizeof(MapIterator), // tp_basicsize
+ 0, // tp_itemsize
+ DeallocMapIterator, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
diff --git a/python/google/protobuf/pyext/map_container.h b/python/google/protobuf/pyext/map_container.h
index 842602e..e14136e 100644
--- a/python/google/protobuf/pyext/map_container.h
+++ b/python/google/protobuf/pyext/map_container.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_MAP_CONTAINER_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_MAP_CONTAINER_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <cstdint>
diff --git a/python/google/protobuf/pyext/message.cc b/python/google/protobuf/pyext/message.cc
index 3a33824..35594ec 100644
--- a/python/google/protobuf/pyext/message.cc
+++ b/python/google/protobuf/pyext/message.cc
@@ -454,11 +454,15 @@
static PyTypeObject _CMessageClass_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".MessageMeta", // tp_name
- sizeof(CMessageClass), // tp_basicsize
- 0, // tp_itemsize
- message_meta::Dealloc, // tp_dealloc
- 0, // tp_print
+ ".MessageMeta", // tp_name
+ sizeof(CMessageClass), // tp_basicsize
+ 0, // tp_itemsize
+ message_meta::Dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, /* tp_print */
+#else
+ 0, /* tp_vectorcall_offset */
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -1930,7 +1934,7 @@
"Error parsing message as the message exceeded the protobuf limit "
"with type '%s'",
self->GetMessageClass()->message_descriptor->full_name().c_str());
- return NULL;
+ return nullptr;
}
// ctx has an explicit limit set (length of string_view), so we have to
@@ -2735,20 +2739,24 @@
sizeof(CMessage), // tp_basicsize
0, // tp_itemsize
(destructor)cmessage::Dealloc, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- (reprfunc)cmessage::ToStr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- PyObject_HashNotImplemented, // tp_hash
- nullptr, // tp_call
- (reprfunc)cmessage::ToStr, // tp_str
- cmessage::GetAttr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ (reprfunc)cmessage::ToStr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ PyObject_HashNotImplemented, // tp_hash
+ nullptr, // tp_call
+ (reprfunc)cmessage::ToStr, // tp_str
+ cmessage::GetAttr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE |
Py_TPFLAGS_HAVE_VERSION_TAG, // tp_flags
"A ProtocolMessage", // tp_doc
diff --git a/python/google/protobuf/pyext/message.h b/python/google/protobuf/pyext/message.h
index 29af255..b17daa5 100644
--- a/python/google/protobuf/pyext/message.h
+++ b/python/google/protobuf/pyext/message.h
@@ -34,6 +34,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <cstdint>
diff --git a/python/google/protobuf/pyext/message_factory.cc b/python/google/protobuf/pyext/message_factory.cc
index 64f9fed..bc44dd4 100644
--- a/python/google/protobuf/pyext/message_factory.cc
+++ b/python/google/protobuf/pyext/message_factory.cc
@@ -30,6 +30,7 @@
#include <unordered_map>
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/dynamic_message.h>
@@ -252,20 +253,24 @@
sizeof(PyMessageFactory), // tp_basicsize
0, // tp_itemsize
message_factory::Dealloc, // tp_dealloc
- 0, // tp_print
- nullptr, // tp_getattr
- nullptr, // tp_setattr
- nullptr, // tp_compare
- nullptr, // tp_repr
- nullptr, // tp_as_number
- nullptr, // tp_as_sequence
- nullptr, // tp_as_mapping
- nullptr, // tp_hash
- nullptr, // tp_call
- nullptr, // tp_str
- nullptr, // tp_getattro
- nullptr, // tp_setattro
- nullptr, // tp_as_buffer
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
+ nullptr, // tp_getattr
+ nullptr, // tp_setattr
+ nullptr, // tp_compare
+ nullptr, // tp_repr
+ nullptr, // tp_as_number
+ nullptr, // tp_as_sequence
+ nullptr, // tp_as_mapping
+ nullptr, // tp_hash
+ nullptr, // tp_call
+ nullptr, // tp_str
+ nullptr, // tp_getattro
+ nullptr, // tp_setattro
+ nullptr, // tp_as_buffer
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, // tp_flags
"A static Message Factory", // tp_doc
message_factory::GcTraverse, // tp_traverse
diff --git a/python/google/protobuf/pyext/message_factory.h b/python/google/protobuf/pyext/message_factory.h
index 515c29c..7dfe425 100644
--- a/python/google/protobuf/pyext/message_factory.h
+++ b/python/google/protobuf/pyext/message_factory.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_FACTORY_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_MESSAGE_FACTORY_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <unordered_map>
diff --git a/python/google/protobuf/pyext/message_module.cc b/python/google/protobuf/pyext/message_module.cc
index 1f953fc..2d3c1d2 100644
--- a/python/google/protobuf/pyext/message_module.cc
+++ b/python/google/protobuf/pyext/message_module.cc
@@ -28,6 +28,7 @@
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <google/protobuf/message_lite.h>
diff --git a/python/google/protobuf/pyext/repeated_composite_container.h b/python/google/protobuf/pyext/repeated_composite_container.h
index e241827..30536ea 100644
--- a/python/google/protobuf/pyext/repeated_composite_container.h
+++ b/python/google/protobuf/pyext/repeated_composite_container.h
@@ -34,6 +34,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_COMPOSITE_CONTAINER_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_COMPOSITE_CONTAINER_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <memory>
diff --git a/python/google/protobuf/pyext/repeated_scalar_container.h b/python/google/protobuf/pyext/repeated_scalar_container.h
index f9f0ea8..372b6f0 100644
--- a/python/google/protobuf/pyext/repeated_scalar_container.h
+++ b/python/google/protobuf/pyext/repeated_scalar_container.h
@@ -34,6 +34,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_SCALAR_CONTAINER_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_REPEATED_SCALAR_CONTAINER_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <memory>
diff --git a/python/google/protobuf/pyext/scoped_pyobject_ptr.h b/python/google/protobuf/pyext/scoped_pyobject_ptr.h
index e6ea7e3..f684152 100644
--- a/python/google/protobuf/pyext/scoped_pyobject_ptr.h
+++ b/python/google/protobuf/pyext/scoped_pyobject_ptr.h
@@ -35,6 +35,7 @@
#include <google/protobuf/stubs/common.h>
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
namespace google {
namespace protobuf {
diff --git a/python/google/protobuf/pyext/unknown_fields.cc b/python/google/protobuf/pyext/unknown_fields.cc
index fbfee3d..dcd63b2 100644
--- a/python/google/protobuf/pyext/unknown_fields.cc
+++ b/python/google/protobuf/pyext/unknown_fields.cc
@@ -30,6 +30,7 @@
#include <google/protobuf/pyext/unknown_fields.h>
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <set>
#include <memory>
@@ -155,11 +156,15 @@
PyTypeObject PyUnknownFields_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".PyUnknownFields", // tp_name
- sizeof(PyUnknownFields), // tp_basicsize
- 0, // tp_itemsize
- unknown_fields::Dealloc, // tp_dealloc
- 0, // tp_print
+ ".PyUnknownFields", // tp_name
+ sizeof(PyUnknownFields), // tp_basicsize
+ 0, // tp_itemsize
+ unknown_fields::Dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
@@ -219,7 +224,7 @@
"The parent message might be cleared.");
return nullptr;
}
- ssize_t total_size = fields->field_count();
+ Py_ssize_t total_size = fields->field_count();
if (self->index >= total_size) {
PyErr_Format(PyExc_ValueError,
"UnknownField does not exist. "
@@ -312,11 +317,15 @@
PyTypeObject PyUnknownFieldRef_Type = {
PyVarObject_HEAD_INIT(&PyType_Type, 0) FULL_MODULE_NAME
- ".PyUnknownFieldRef", // tp_name
- sizeof(PyUnknownFieldRef), // tp_basicsize
- 0, // tp_itemsize
- unknown_field::Dealloc, // tp_dealloc
- 0, // tp_print
+ ".PyUnknownFieldRef", // tp_name
+ sizeof(PyUnknownFieldRef), // tp_basicsize
+ 0, // tp_itemsize
+ unknown_field::Dealloc, // tp_dealloc
+#if PY_VERSION_HEX < 0x03080000
+ nullptr, // tp_print
+#else
+ 0, // tp_vectorcall_offset
+#endif
nullptr, // tp_getattr
nullptr, // tp_setattr
nullptr, // tp_compare
diff --git a/python/google/protobuf/pyext/unknown_fields.h b/python/google/protobuf/pyext/unknown_fields.h
index 94d55e1..e7b0b35 100644
--- a/python/google/protobuf/pyext/unknown_fields.h
+++ b/python/google/protobuf/pyext/unknown_fields.h
@@ -31,6 +31,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_CPP_UNKNOWN_FIELDS_H__
#define GOOGLE_PROTOBUF_PYTHON_CPP_UNKNOWN_FIELDS_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
#include <memory>
diff --git a/python/google/protobuf/python_protobuf.h b/python/google/protobuf/python_protobuf.h
index 8db1ffb..4fcf065 100644
--- a/python/google/protobuf/python_protobuf.h
+++ b/python/google/protobuf/python_protobuf.h
@@ -36,6 +36,7 @@
#ifndef GOOGLE_PROTOBUF_PYTHON_PYTHON_PROTOBUF_H__
#define GOOGLE_PROTOBUF_PYTHON_PYTHON_PROTOBUF_H__
+#define PY_SSIZE_T_CLEAN
#include <Python.h>
namespace google {
diff --git a/python/google/protobuf/service_reflection.py b/python/google/protobuf/service_reflection.py
index 75c51ff..f82ab71 100644
--- a/python/google/protobuf/service_reflection.py
+++ b/python/google/protobuf/service_reflection.py
@@ -133,7 +133,7 @@
"""
self.descriptor = service_descriptor
- def BuildService(self, cls):
+ def BuildService(builder, cls):
"""Constructs the service class.
Args:
@@ -143,18 +143,26 @@
# CallMethod needs to operate with an instance of the Service class. This
# internal wrapper function exists only to be able to pass the service
# instance to the method that does the real CallMethod work.
- def _WrapCallMethod(srvc, method_descriptor,
- rpc_controller, request, callback):
- return self._CallMethod(srvc, method_descriptor,
- rpc_controller, request, callback)
- self.cls = cls
+ # Making sure to use exact argument names from the abstract interface in
+ # service.py to match the type signature
+ def _WrapCallMethod(self, method_descriptor, rpc_controller, request, done):
+ return builder._CallMethod(self, method_descriptor, rpc_controller,
+ request, done)
+
+ def _WrapGetRequestClass(self, method_descriptor):
+ return builder._GetRequestClass(method_descriptor)
+
+ def _WrapGetResponseClass(self, method_descriptor):
+ return builder._GetResponseClass(method_descriptor)
+
+ builder.cls = cls
cls.CallMethod = _WrapCallMethod
- cls.GetDescriptor = staticmethod(lambda: self.descriptor)
- cls.GetDescriptor.__doc__ = "Returns the service descriptor."
- cls.GetRequestClass = self._GetRequestClass
- cls.GetResponseClass = self._GetResponseClass
- for method in self.descriptor.methods:
- setattr(cls, method.name, self._GenerateNonImplementedMethod(method))
+ cls.GetDescriptor = staticmethod(lambda: builder.descriptor)
+ cls.GetDescriptor.__doc__ = 'Returns the service descriptor.'
+ cls.GetRequestClass = _WrapGetRequestClass
+ cls.GetResponseClass = _WrapGetResponseClass
+ for method in builder.descriptor.methods:
+ setattr(cls, method.name, builder._GenerateNonImplementedMethod(method))
def _CallMethod(self, srvc, method_descriptor,
rpc_controller, request, callback):
diff --git a/python/setup.py b/python/setup.py
index ab42b6f..fb35cf5 100755
--- a/python/setup.py
+++ b/python/setup.py
@@ -1,6 +1,9 @@
#! /usr/bin/env python
#
# See README for usage instructions.
+
+# pylint:disable=missing-module-docstring
+# pylint:disable=g-bad-import-order
from distutils import util
import fnmatch
import glob
@@ -10,7 +13,9 @@
import subprocess
import sys
import sysconfig
-import platform
+
+# pylint:disable=g-importing-member
+# pylint:disable=g-multiple-import
# We must use setuptools, not distutils, because we need to use the
# namespace_packages option for the "google" package.
@@ -24,44 +29,52 @@
# Find the Protocol Compiler.
if 'PROTOC' in os.environ and os.path.exists(os.environ['PROTOC']):
protoc = os.environ['PROTOC']
-elif os.path.exists("../src/protoc"):
- protoc = "../src/protoc"
-elif os.path.exists("../src/protoc.exe"):
- protoc = "../src/protoc.exe"
-elif os.path.exists("../vsprojects/Debug/protoc.exe"):
- protoc = "../vsprojects/Debug/protoc.exe"
-elif os.path.exists("../vsprojects/Release/protoc.exe"):
- protoc = "../vsprojects/Release/protoc.exe"
+elif os.path.exists('../src/protoc'):
+ protoc = '../src/protoc'
+elif os.path.exists('../src/protoc.exe'):
+ protoc = '../src/protoc.exe'
+elif os.path.exists('../vsprojects/Debug/protoc.exe'):
+ protoc = '../vsprojects/Debug/protoc.exe'
+elif os.path.exists('../vsprojects/Release/protoc.exe'):
+ protoc = '../vsprojects/Release/protoc.exe'
else:
- protoc = find_executable("protoc")
+ protoc = find_executable('protoc')
def GetVersion():
- """Gets the version from google/protobuf/__init__.py
+ """Reads and returns the version from google/protobuf/__init__.py.
Do not import google.protobuf.__init__ directly, because an installed
- protobuf library may be loaded instead."""
+ protobuf library may be loaded instead.
+
+ Returns:
+ The version.
+ """
with open(os.path.join('google', 'protobuf', '__init__.py')) as version_file:
- exec(version_file.read(), globals())
- global __version__
- return __version__
+ exec(version_file.read(), globals()) # pylint:disable=exec-used
+ return __version__ # pylint:disable=undefined-variable
-def generate_proto(source, require = True):
- """Invokes the Protocol Compiler to generate a _pb2.py from the given
- .proto file. Does nothing if the output already exists and is newer than
- the input."""
+def GenProto(source, require=True):
+ """Generates a _pb2.py from the given .proto file.
+
+ Does nothing if the output already exists and is newer than the input.
+
+ Args:
+ source: the .proto file path.
+ require: if True, exit immediately when a path is not found.
+ """
if not require and not os.path.exists(source):
return
- output = source.replace(".proto", "_pb2.py").replace("../src/", "")
+ output = source.replace('.proto', '_pb2.py').replace('../src/', '')
if (not os.path.exists(output) or
(os.path.exists(source) and
os.path.getmtime(source) > os.path.getmtime(output))):
- print("Generating %s..." % output)
+ print('Generating %s...' % output)
if not os.path.exists(source):
sys.stderr.write("Can't find required file: %s\n" % source)
@@ -69,78 +82,85 @@
if protoc is None:
sys.stderr.write(
- "protoc is not installed nor found in ../src. Please compile it "
- "or install the binary package.\n")
+ 'protoc is not installed nor found in ../src. Please compile it '
+ 'or install the binary package.\n')
sys.exit(-1)
- protoc_command = [ protoc, "-I../src", "-I.", "--python_out=.", source ]
+ protoc_command = [protoc, '-I../src', '-I.', '--python_out=.', source]
if subprocess.call(protoc_command) != 0:
sys.exit(-1)
+
def GenerateUnittestProtos():
- generate_proto("../src/google/protobuf/any_test.proto", False)
- generate_proto("../src/google/protobuf/map_proto2_unittest.proto", False)
- generate_proto("../src/google/protobuf/map_unittest.proto", False)
- generate_proto("../src/google/protobuf/test_messages_proto3.proto", False)
- generate_proto("../src/google/protobuf/test_messages_proto2.proto", False)
- generate_proto("../src/google/protobuf/unittest_arena.proto", False)
- generate_proto("../src/google/protobuf/unittest.proto", False)
- generate_proto("../src/google/protobuf/unittest_custom_options.proto", False)
- generate_proto("../src/google/protobuf/unittest_import.proto", False)
- generate_proto("../src/google/protobuf/unittest_import_public.proto", False)
- generate_proto("../src/google/protobuf/unittest_mset.proto", False)
- generate_proto("../src/google/protobuf/unittest_mset_wire_format.proto", False)
- generate_proto("../src/google/protobuf/unittest_no_generic_services.proto", False)
- generate_proto("../src/google/protobuf/unittest_proto3_arena.proto", False)
- generate_proto("../src/google/protobuf/util/json_format.proto", False)
- generate_proto("../src/google/protobuf/util/json_format_proto3.proto", False)
- generate_proto("google/protobuf/internal/any_test.proto", False)
- generate_proto("google/protobuf/internal/descriptor_pool_test1.proto", False)
- generate_proto("google/protobuf/internal/descriptor_pool_test2.proto", False)
- generate_proto("google/protobuf/internal/factory_test1.proto", False)
- generate_proto("google/protobuf/internal/factory_test2.proto", False)
- generate_proto("google/protobuf/internal/file_options_test.proto", False)
- generate_proto("google/protobuf/internal/import_test_package/inner.proto", False)
- generate_proto("google/protobuf/internal/import_test_package/outer.proto", False)
- generate_proto("google/protobuf/internal/missing_enum_values.proto", False)
- generate_proto("google/protobuf/internal/message_set_extensions.proto", False)
- generate_proto("google/protobuf/internal/more_extensions.proto", False)
- generate_proto("google/protobuf/internal/more_extensions_dynamic.proto", False)
- generate_proto("google/protobuf/internal/more_messages.proto", False)
- generate_proto("google/protobuf/internal/no_package.proto", False)
- generate_proto("google/protobuf/internal/packed_field_test.proto", False)
- generate_proto("google/protobuf/internal/test_bad_identifiers.proto", False)
- generate_proto("google/protobuf/internal/test_proto3_optional.proto", False)
- generate_proto("google/protobuf/pyext/python.proto", False)
+ """Generates protobuf code for unittests."""
+ GenProto('../src/google/protobuf/any_test.proto', False)
+ GenProto('../src/google/protobuf/map_proto2_unittest.proto', False)
+ GenProto('../src/google/protobuf/map_unittest.proto', False)
+ GenProto('../src/google/protobuf/test_messages_proto3.proto', False)
+ GenProto('../src/google/protobuf/test_messages_proto2.proto', False)
+ GenProto('../src/google/protobuf/unittest_arena.proto', False)
+ GenProto('../src/google/protobuf/unittest.proto', False)
+ GenProto('../src/google/protobuf/unittest_custom_options.proto', False)
+ GenProto('../src/google/protobuf/unittest_import.proto', False)
+ GenProto('../src/google/protobuf/unittest_import_public.proto', False)
+ GenProto('../src/google/protobuf/unittest_mset.proto', False)
+ GenProto('../src/google/protobuf/unittest_mset_wire_format.proto', False)
+ GenProto('../src/google/protobuf/unittest_no_generic_services.proto', False)
+ GenProto('../src/google/protobuf/unittest_proto3_arena.proto', False)
+ GenProto('../src/google/protobuf/util/json_format.proto', False)
+ GenProto('../src/google/protobuf/util/json_format_proto3.proto', False)
+ GenProto('google/protobuf/internal/any_test.proto', False)
+ GenProto('google/protobuf/internal/descriptor_pool_test1.proto', False)
+ GenProto('google/protobuf/internal/descriptor_pool_test2.proto', False)
+ GenProto('google/protobuf/internal/factory_test1.proto', False)
+ GenProto('google/protobuf/internal/factory_test2.proto', False)
+ GenProto('google/protobuf/internal/file_options_test.proto', False)
+ GenProto('google/protobuf/internal/import_test_package/inner.proto', False)
+ GenProto('google/protobuf/internal/import_test_package/outer.proto', False)
+ GenProto('google/protobuf/internal/missing_enum_values.proto', False)
+ GenProto('google/protobuf/internal/message_set_extensions.proto', False)
+ GenProto('google/protobuf/internal/more_extensions.proto', False)
+ GenProto('google/protobuf/internal/more_extensions_dynamic.proto', False)
+ GenProto('google/protobuf/internal/more_messages.proto', False)
+ GenProto('google/protobuf/internal/no_package.proto', False)
+ GenProto('google/protobuf/internal/packed_field_test.proto', False)
+ GenProto('google/protobuf/internal/test_bad_identifiers.proto', False)
+ GenProto('google/protobuf/internal/test_proto3_optional.proto', False)
+ GenProto('google/protobuf/pyext/python.proto', False)
-class clean(_clean):
+class CleanCmd(_clean):
+ """Custom clean command for building the protobuf extension."""
+
def run(self):
# Delete generated files in the code tree.
- for (dirpath, dirnames, filenames) in os.walk("."):
+ for (dirpath, unused_dirnames, filenames) in os.walk('.'):
for filename in filenames:
filepath = os.path.join(dirpath, filename)
- if filepath.endswith("_pb2.py") or filepath.endswith(".pyc") or \
- filepath.endswith(".so") or filepath.endswith(".o"):
+ if (filepath.endswith('_pb2.py') or filepath.endswith('.pyc') or
+ filepath.endswith('.so') or filepath.endswith('.o')):
os.remove(filepath)
# _clean is an old-style class, so super() doesn't work.
_clean.run(self)
-class build_py(_build_py):
+
+class BuildPyCmd(_build_py):
+ """Custom build_py command for building the protobuf runtime."""
+
def run(self):
# Generate necessary .proto file if it doesn't exist.
- generate_proto("../src/google/protobuf/descriptor.proto")
- generate_proto("../src/google/protobuf/compiler/plugin.proto")
- generate_proto("../src/google/protobuf/any.proto")
- generate_proto("../src/google/protobuf/api.proto")
- generate_proto("../src/google/protobuf/duration.proto")
- generate_proto("../src/google/protobuf/empty.proto")
- generate_proto("../src/google/protobuf/field_mask.proto")
- generate_proto("../src/google/protobuf/source_context.proto")
- generate_proto("../src/google/protobuf/struct.proto")
- generate_proto("../src/google/protobuf/timestamp.proto")
- generate_proto("../src/google/protobuf/type.proto")
- generate_proto("../src/google/protobuf/wrappers.proto")
+ GenProto('../src/google/protobuf/descriptor.proto')
+ GenProto('../src/google/protobuf/compiler/plugin.proto')
+ GenProto('../src/google/protobuf/any.proto')
+ GenProto('../src/google/protobuf/api.proto')
+ GenProto('../src/google/protobuf/duration.proto')
+ GenProto('../src/google/protobuf/empty.proto')
+ GenProto('../src/google/protobuf/field_mask.proto')
+ GenProto('../src/google/protobuf/source_context.proto')
+ GenProto('../src/google/protobuf/struct.proto')
+ GenProto('../src/google/protobuf/timestamp.proto')
+ GenProto('../src/google/protobuf/type.proto')
+ GenProto('../src/google/protobuf/wrappers.proto')
GenerateUnittestProtos()
# _build_py is an old-style class, so super() doesn't work.
@@ -148,17 +168,18 @@
def find_package_modules(self, package, package_dir):
exclude = (
- "*test*",
- "google/protobuf/internal/*_pb2.py",
- "google/protobuf/internal/_parameterized.py",
- "google/protobuf/pyext/python_pb2.py",
+ '*test*',
+ 'google/protobuf/internal/*_pb2.py',
+ 'google/protobuf/internal/_parameterized.py',
+ 'google/protobuf/pyext/python_pb2.py',
)
modules = _build_py.find_package_modules(self, package, package_dir)
return [(pkg, mod, fil) for (pkg, mod, fil) in modules
if not any(fnmatch.fnmatchcase(fil, pat=pat) for pat in exclude)]
-class build_ext(_build_ext):
+class BuildExtCmd(_build_ext):
+ """Command class for building the protobuf Python extension."""
def get_ext_filename(self, ext_name):
# since python3.5, python extensions' shared libraries use a suffix that
@@ -169,23 +190,25 @@
# suffix so that the resulting file name matches the target architecture
# and we end up with a well-formed wheel.
filename = _build_ext.get_ext_filename(self, ext_name)
- orig_ext_suffix = sysconfig.get_config_var("EXT_SUFFIX")
- new_ext_suffix = os.getenv("PROTOCOL_BUFFERS_OVERRIDE_EXT_SUFFIX")
+ orig_ext_suffix = sysconfig.get_config_var('EXT_SUFFIX')
+ new_ext_suffix = os.getenv('PROTOCOL_BUFFERS_OVERRIDE_EXT_SUFFIX')
if new_ext_suffix and filename.endswith(orig_ext_suffix):
filename = filename[:-len(orig_ext_suffix)] + new_ext_suffix
return filename
-class test_conformance(_build_py):
+
+class TestConformanceCmd(_build_py):
target = 'test_python'
+
def run(self):
# Python 2.6 dodges these extra failures.
- os.environ["CONFORMANCE_PYTHON_EXTRA_FAILURES"] = (
- "--failure_list failure_list_python-post26.txt")
- cmd = 'cd ../conformance && make %s' % (test_conformance.target)
- status = subprocess.check_call(cmd, shell=True)
+ os.environ['CONFORMANCE_PYTHON_EXTRA_FAILURES'] = (
+ '--failure_list failure_list_python-post26.txt')
+ cmd = 'cd ../conformance && make %s' % (TestConformanceCmd.target)
+ subprocess.check_call(cmd, shell=True)
-def get_option_from_sys_argv(option_str):
+def GetOptionFromArgv(option_str):
if option_str in sys.argv:
sys.argv.remove(option_str)
return True
@@ -195,21 +218,37 @@
if __name__ == '__main__':
ext_module_list = []
warnings_as_errors = '--warnings_as_errors'
- if get_option_from_sys_argv('--cpp_implementation'):
+ if GetOptionFromArgv('--cpp_implementation'):
# Link libprotobuf.a and libprotobuf-lite.a statically with the
# extension. Note that those libraries have to be compiled with
# -fPIC for this to work.
- compile_static_ext = get_option_from_sys_argv('--compile_static_extension')
+ compile_static_ext = GetOptionFromArgv('--compile_static_extension')
libraries = ['protobuf']
extra_objects = None
if compile_static_ext:
libraries = None
extra_objects = ['../src/.libs/libprotobuf.a',
'../src/.libs/libprotobuf-lite.a']
- test_conformance.target = 'test_python_cpp'
+ TestConformanceCmd.target = 'test_python_cpp'
extra_compile_args = []
+ message_extra_link_args = None
+ api_implementation_link_args = None
+ if 'darwin' in sys.platform:
+ if sys.version_info[0] == 2:
+ message_init_symbol = 'init_message'
+ api_implementation_init_symbol = 'init_api_implementation'
+ else:
+ message_init_symbol = 'PyInit__message'
+ api_implementation_init_symbol = 'PyInit__api_implementation'
+ message_extra_link_args = [
+ '-Wl,-exported_symbol,_%s' % message_init_symbol
+ ]
+ api_implementation_link_args = [
+ '-Wl,-exported_symbol,_%s' % api_implementation_init_symbol
+ ]
+
if sys.platform != 'win32':
extra_compile_args.append('-Wno-write-strings')
extra_compile_args.append('-Wno-invalid-offsetof')
@@ -218,8 +257,8 @@
extra_compile_args.append('-std=c++11')
if sys.platform == 'darwin':
- extra_compile_args.append("-Wno-shorten-64-to-32");
- extra_compile_args.append("-Wno-deprecated-register");
+ extra_compile_args.append('-Wno-shorten-64-to-32')
+ extra_compile_args.append('-Wno-deprecated-register')
# https://developer.apple.com/documentation/xcode_release_notes/xcode_10_release_notes
# C++ projects must now migrate to libc++ and are recommended to set a
@@ -227,7 +266,7 @@
if sys.platform == 'darwin':
mac_target = str(sysconfig.get_config_var('MACOSX_DEPLOYMENT_TARGET'))
if mac_target and (pkg_resources.parse_version(mac_target) <
- pkg_resources.parse_version('10.9.0')):
+ pkg_resources.parse_version('10.9.0')):
os.environ['MACOSX_DEPLOYMENT_TARGET'] = '10.9'
os.environ['_PYTHON_HOST_PLATFORM'] = re.sub(
r'macosx-[0-9]+\.[0-9]+-(.+)', r'macosx-10.9-\1',
@@ -242,10 +281,10 @@
extra_compile_args.append('-DMS_WIN64')
# MSVS default is dymanic
- if (sys.platform == 'win32'):
+ if sys.platform == 'win32':
extra_compile_args.append('/MT')
- if "clang" in os.popen('$CC --version 2> /dev/null').read():
+ if 'clang' in os.popen('$CC --version 2> /dev/null').read():
extra_compile_args.append('-Wno-shorten-64-to-32')
if warnings_as_errors in sys.argv:
@@ -255,18 +294,21 @@
# C++ implementation extension
ext_module_list.extend([
Extension(
- "google.protobuf.pyext._message",
+ 'google.protobuf.pyext._message',
glob.glob('google/protobuf/pyext/*.cc'),
- include_dirs=[".", "../src"],
+ include_dirs=['.', '../src'],
libraries=libraries,
extra_objects=extra_objects,
+ extra_link_args=message_extra_link_args,
library_dirs=['../src/.libs'],
extra_compile_args=extra_compile_args,
),
Extension(
- "google.protobuf.internal._api_implementation",
+ 'google.protobuf.internal._api_implementation',
glob.glob('google/protobuf/internal/api_implementation.cc'),
- extra_compile_args=extra_compile_args + ['-DPYTHON_PROTO2_CPP_IMPL_V2'],
+ extra_compile_args=(extra_compile_args +
+ ['-DPYTHON_PROTO2_CPP_IMPL_V2']),
+ extra_link_args=api_implementation_link_args,
),
])
os.environ['PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION'] = 'cpp'
@@ -283,15 +325,14 @@
url='https://developers.google.com/protocol-buffers/',
maintainer='protobuf@googlegroups.com',
maintainer_email='protobuf@googlegroups.com',
- license='3-Clause BSD License',
+ license='BSD-3-Clause',
classifiers=[
- "Programming Language :: Python",
- "Programming Language :: Python :: 3",
- "Programming Language :: Python :: 3.3",
- "Programming Language :: Python :: 3.4",
- "Programming Language :: Python :: 3.5",
- "Programming Language :: Python :: 3.6",
- "Programming Language :: Python :: 3.7",
+ 'Programming Language :: Python',
+ 'Programming Language :: Python :: 3',
+ 'Programming Language :: Python :: 3.7',
+ 'Programming Language :: Python :: 3.8',
+ 'Programming Language :: Python :: 3.9',
+ 'Programming Language :: Python :: 3.10',
],
namespace_packages=['google'],
packages=find_packages(
@@ -301,12 +342,12 @@
],),
test_suite='google.protobuf.internal',
cmdclass={
- 'clean': clean,
- 'build_py': build_py,
- 'build_ext': build_ext,
- 'test_conformance': test_conformance,
+ 'clean': CleanCmd,
+ 'build_py': BuildPyCmd,
+ 'build_ext': BuildExtCmd,
+ 'test_conformance': TestConformanceCmd,
},
install_requires=install_requires,
ext_modules=ext_module_list,
- python_requires=">=3.5",
+ python_requires='>=3.7',
)