I see, the problem is that you've created a copy of descriptor.proto and are
extending that rather than extending the original file.
To correctly extend descriptor.proto, you need to import it like:
import "google/protobuf/descriptor.proto";
The path name is important, because it determines which module your
generated code imports and extends. You want it to import
google.protobuf.descriptor_pb2 (which is included in the protobuf library),
not your own local copy of descriptor_pb2.
Note that when you install protocol buffers, a copy of descriptor.proto is
placed in $PREFIX/include/google/protobuf (where $PREFIX is usually /usr or
/usr/local). So you should invoke protoc like:
protoc -I. -I/usr/include ooo.proto
This way ooo.proto will be able to import google/protobuf/descriptor.proto,
which protoc will find in /usr/include.
On Thu, Nov 18, 2010 at 4:32 AM, Vsevolod Zadubrovsky wrote:
> Kenton,
>
> I didn't find how to attach file in the group discussion, so am replying to
> you directly.
> In attach you will find the source proto file, the generated *pb2.py files,
> and the test program enum_test.py
> I used: google protobuf 2.3.0 and proto compiler 2.3.0 win32 from here:
> http://code.google.com/p/protobuf/downloads/list
>
> The test output is:
>
> E:\projects\gpb>python enum_test.py
> serialized request☺►☻:
> Traceback (most recent call last):
> File "enum_test.py", line 13, in ext =
> opts.Extensions[proto.verbose_enum_value_option]
> File
> "C:\Python27\lib\site-packages\protobuf-2.3.0-py2.7.egg\google\protobuf\reflection.py",
> line 1068, in __getitem__
> _VerifyExtensionHandle(self._extended_message, extension_handle)
> File
> "C:\Python27\lib\site-packages\protobuf-2.3.0-py2.7.egg\google\protobuf\reflection.py",
> line 229, in _VerifyExtensionHandle
> message.DESCRIPTOR.full_name))
>
> KeyError: 'Extension "verbose_enum_value_option" extends message type
> "google.protobuf.EnumValueOptions", but this message is of type
> "google.protobuf.EnumValueOptions".'
>
> Thnk you very much for support
>
> 2010/11/17 Kenton Varda
>
> That is strange. Can you provide a minimal but complete program that
>> reproduces this problem, so I can look at it?
>>
>> On Wed, Nov 10, 2010 at 12:42 AM, Vsevolod Zadubrovsky <
>> zadubrov...@gmail.com> wrote:
>>
>>> It seems to me, it doesn't work at all.
>>>
>>> I got this:
>>> >(Pdb) import ooo
>>> >(Pdb) vals_by_nums =
>>> req.DESCRIPTOR.fields_by_name['error'].enum_type.values_by_number[req.error]
>>> >(Pdb) options = vals_by_nums.GetOptions()
>>> >(Pdb) options.Extensions[ooo.verbose_enum_value_option]
>>> *** KeyError: 'Extension "verbose_enum_value_option" extends message
>>> type "google.protobuf.EnumValueOptions", but this message is of type
>>> "google.protobuf.EnumValueOptions".'
>>>
>>> I've checked the source code, and it looks like raised from here
>>> (google.protobuf.reflection, line 224):
>>>
>>> if extension_handle.containing_type is not message.DESCRIPTOR:
>>>raise KeyError('Extension "%s" extends message type "%s", but this
>>> '
>>> 'message is of type "%s".' %
>>> (extension_handle.full_name,
>>>extension_handle.containing_type.full_name,
>>>message.DESCRIPTOR.full_name))
>>>
>>> Any ideas ? may be it is already solved in trunk version?
>>>
>>> Thanks
>>>
>>>
>>> On Nov 10, 1:50 am, Kenton Varda wrote:
>>> > You need to use the descriptor for the enum type. Unfortunately this
>>> > interface isn't very well fleshed-out in Python. I think you'd have to
>>> > write something like:
>>> >
>>> >
>>> Request.DESCRIPTOR.fields_by_name['error'].enum_type.values_by_number[message.error].options.Extensions[verbose_enum_value_option]
>>> >
>>> > I haven't checked that that's exactly correct, but it gives you an
>>> idea. We
>>> > should probably improve this.
>>> >
>>> > On Tue, Nov 9, 2010 at 4:12 AM, Vsevolod Zadubrovsky
>>> > wrote:
>>>
>>> >
>>> > > Hi, I'm stuck with getting the enum value option in Python. The proto
>>> > > file is:
>>> >
>>> > > import "descriptor.proto";
>>> >
>>> > > extend google.protobuf.EnumValueOptions {
>>> > > optional string verbose_enum_value_option = 50005;
>>> > > }
>>> >
>>> > > enum ErrorType {
>>> > >OK = 1 [(verbose_enum_value_option) = "OK"];
>>> > >SOME_ERROR = 2 [(verbose_enum_value_option) = "Some Error
>>> verbose
>>> > > message"];
>>> > > }
>>> >
>>> > > message Request {
>>> > > required bool success = 1;
>>> > > optional ErrorType error = 2;
>>> > > }
>>> >
>>> > > When I receive the Request message, I can access the 'error' field,
>>> > > and its type is int, that's actually ok. But how can I get the
>>> > > verbose_enum_value_option of 'error' field value ?
>>> >
>>> > > Thanks
>>> >
>>> > > p.s. The goal is to keep error types and their verbose error messages
>>> > > in one place, available for every service in our project, so the
>>> error
>>> > > messages would've been identical.