1818#include " absl/log/check.h"
1919#include " absl/log/log.h"
2020#include " absl/memory/memory.h"
21+ #include " absl/strings/match.h"
22+ #include " absl/strings/str_cat.h"
2123#include " absl/strings/str_replace.h"
2224#include " absl/strings/string_view.h"
25+ #include " absl/strings/strip.h"
2326#include " absl/types/optional.h"
2427#include " google/protobuf/descriptor.h"
2528#include " google/protobuf/descriptor_database.h"
@@ -46,16 +49,24 @@ using ::google::protobuf::python::PyProto_API;
4649using ::google::protobuf::python::PyProtoAPICapsuleName;
4750
4851namespace pybind11_protobuf {
49- namespace {
5052
51- std::string PythonPackageForDescriptor (const FileDescriptor* file) {
52- std::vector<std::pair<const absl::string_view, std::string>> replacements;
53- replacements.emplace_back (" /" , " ." );
54- replacements.emplace_back (" .proto" , " _pb2" );
55- std::string name = file->name ();
56- return absl::StrReplaceAll (name, replacements);
53+ std::string StripProtoSuffixFromDescriptorFileName (absl::string_view filename) {
54+ if (absl::EndsWith (filename, " .protodevel" )) {
55+ return std::string (absl::StripSuffix (filename, " .protodevel" ));
56+ } else {
57+ return std::string (absl::StripSuffix (filename, " .proto" ));
58+ }
59+ }
60+
61+ std::string InferPythonModuleNameFromDescriptorFileName (
62+ absl::string_view filename) {
63+ std::string basename = StripProtoSuffixFromDescriptorFileName (filename);
64+ absl::StrReplaceAll ({{" -" , " _" }, {" /" , " ." }}, &basename);
65+ return absl::StrCat (basename, " _pb2" );
5766}
5867
68+ namespace {
69+
5970// Resolves the class name of a descriptor via d->containing_type()
6071py::object ResolveDescriptor (py::object p, const Descriptor* d) {
6172 return d->containing_type () ? ResolveDescriptor (p, d->containing_type ())
@@ -299,7 +310,8 @@ py::module_ GlobalState::ImportCached(const std::string& module_name) {
299310}
300311
301312py::object GlobalState::PyMessageInstance (const Descriptor* descriptor) {
302- auto module_name = PythonPackageForDescriptor (descriptor->file ());
313+ auto module_name =
314+ InferPythonModuleNameFromDescriptorFileName (descriptor->file ()->name ());
303315 if (!module_name.empty ()) {
304316 auto cached = import_cache_.find (module_name);
305317 if (cached != import_cache_.end ()) {
@@ -567,7 +579,8 @@ void InitializePybindProtoCastUtil() {
567579void ImportProtoDescriptorModule (const Descriptor* descriptor) {
568580 assert (PyGILState_Check ());
569581 if (!descriptor) return ;
570- auto module_name = PythonPackageForDescriptor (descriptor->file ());
582+ auto module_name =
583+ InferPythonModuleNameFromDescriptorFileName (descriptor->file ()->name ());
571584 if (module_name.empty ()) return ;
572585 try {
573586 GlobalState::instance ()->ImportCached (module_name);
0 commit comments