Skip to content

Commit a785848

Browse files
evalon32copybara-github
authored andcommitted
Prepare code for breaking change in Protobuf C++ API.
Protobuf 6.30.0 will change the return types of `Descriptor::name()` and other methods to `absl::string_view`. This makes the code work both before and after such a change. PiperOrigin-RevId: 675328307
1 parent f1b2459 commit a785848

File tree

1 file changed

+17
-16
lines changed

1 file changed

+17
-16
lines changed

pybind11_protobuf/proto_utils.cc

Lines changed: 17 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include "google/protobuf/descriptor.h"
1717
#include "google/protobuf/message.h"
1818
#include "google/protobuf/reflection.h"
19+
#include "absl/strings/str_cat.h"
1920
#include "absl/strings/string_view.h"
2021

2122
namespace pybind11 {
@@ -45,9 +46,9 @@ void ProtoSetField(::google::protobuf::Message* message,
4546
bool PyProtoFullName(handle py_proto, std::string* name);
4647

4748
// Returns whether py_proto is a proto and matches the expected_type.
48-
bool PyProtoCheckType(handle py_proto, const std::string& expected_type);
49+
bool PyProtoCheckType(handle py_proto, absl::string_view expected_type);
4950
// Throws a type error if py_proto is not a proto or the wrong message type.
50-
void PyProtoCheckTypeOrThrow(handle py_proto, const std::string& expected_type);
51+
void PyProtoCheckTypeOrThrow(handle py_proto, absl::string_view expected_type);
5152

5253
// Returns whether py_proto is a proto and matches the ProtoType.
5354
template <typename ProtoType>
@@ -419,7 +420,9 @@ class ProtoFieldContainer<GenericEnum> : public ProtoFieldContainerBase {
419420
void Append(handle value) {
420421
reflection_->AddEnumValue(proto_, field_desc_, CastOrTypeError<int>(value));
421422
}
422-
std::string ElementRepr(int idx) const { return GetDesc(idx)->name(); }
423+
std::string ElementRepr(int idx) const {
424+
return std::string(GetDesc(idx)->name());
425+
}
423426
};
424427

425428
// A container for a repeated field.
@@ -677,10 +680,8 @@ const ::google::protobuf::FieldDescriptor* GetFieldDescriptor(
677680
message->GetDescriptor()->FindFieldByName(std::string(name));
678681

679682
if (!field_desc) {
680-
std::string error_str =
681-
"'" + message->GetTypeName() + "' object has no attribute '";
682-
error_str.append(std::string(name));
683-
error_str.append("'");
683+
std::string error_str = absl::StrCat(
684+
"'", message->GetTypeName(), "' object has no attribute '", name, "'");
684685
PyErr_SetString(error_type, error_str.c_str());
685686
throw error_already_set();
686687
}
@@ -736,23 +737,22 @@ bool PyProtoFullName(handle py_proto, std::string* name) {
736737
return false;
737738
}
738739

739-
bool PyProtoCheckType(handle py_proto, const std::string& expected_type) {
740+
bool PyProtoCheckType(handle py_proto, absl::string_view expected_type) {
740741
std::string name;
741742
if (PyProtoFullName(py_proto, &name)) return name == expected_type;
742743
return false;
743744
}
744745

745-
void PyProtoCheckTypeOrThrow(handle py_proto,
746-
const std::string& expected_type) {
746+
void PyProtoCheckTypeOrThrow(handle py_proto, absl::string_view expected_type) {
747747
std::string name;
748748
if (!PyProtoFullName(py_proto, &name)) {
749749
auto builtins = module::import(PYBIND11_BUILTINS_MODULE);
750750
std::string type_str =
751751
str(builtins.attr("repr")(builtins.attr("type")(py_proto)));
752752
throw type_error("Expected a proto, got a " + type_str + ".");
753753
} else if (name != expected_type) {
754-
throw type_error("Passed proto is the wrong type. Expected " +
755-
expected_type + " but got " + name + ".");
754+
throw type_error(absl::StrCat("Passed proto is the wrong type. Expected ",
755+
expected_type, " but got ", name, "."));
756756
}
757757
}
758758

@@ -798,8 +798,8 @@ std::unique_ptr<::google::protobuf::Message> PyProtoAllocateMessage(
798798
::google::protobuf::MessageFactory::generated_factory()->GetPrototype(descriptor);
799799
if (!prototype) {
800800
throw std::runtime_error(
801-
"Not able to generate prototype for descriptor of: " +
802-
descriptor->full_name());
801+
absl::StrCat("Not able to generate prototype for descriptor of: ",
802+
descriptor->full_name()));
803803
}
804804
auto message = std::unique_ptr<::google::protobuf::Message>(prototype->New());
805805
ProtoInitFields(message.get(), kwargs_in);
@@ -824,8 +824,9 @@ void ProtoSetField(::google::protobuf::Message* message,
824824
const ::google::protobuf::FieldDescriptor* field_desc, handle value) {
825825
if (field_desc->is_map() || field_desc->is_repeated() ||
826826
field_desc->type() == ::google::protobuf::FieldDescriptor::TYPE_MESSAGE) {
827-
std::string error = "Assignment not allowed to field \"" +
828-
field_desc->name() + "\" in protocol message object.";
827+
std::string error =
828+
absl::StrCat("Assignment not allowed to field \"", field_desc->name(),
829+
"\" in protocol message object.");
829830
PyErr_SetString(PyExc_AttributeError, error.c_str());
830831
throw error_already_set();
831832
}

0 commit comments

Comments
 (0)