Skip to content

extending existing enum #6104

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
timestee opened this issue May 5, 2019 · 7 comments
Closed

extending existing enum #6104

timestee opened this issue May 5, 2019 · 7 comments

Comments

@timestee
Copy link

timestee commented May 5, 2019

Is there any way to extend enum?
E.g.
I would have enum ErrorCode in the first file as for the underlying message ErrorResponse.

message ErrorResponse {
    ErrorCode code = 1;
    string message = 2;
}
enum ErrorCode {
    OK = 0;
    UNKNOWN = 1;
}

And also i want exted the enum in the second file like this:

enum ErrorCode {
    UserNotFound = 1001;
}

Is it possible at all?
Any workarounds?

@timestee timestee changed the title extending existed enum extending existing enum May 5, 2019
@acozzette
Copy link
Member

There is no way to define an enum in one file and then extend it with additional values in another file. You can extend messages, though--would that work for your use case?

@timestee
Copy link
Author

timestee commented May 7, 2019

would that work for your use case?
perhaps not work for me, actually i want to define all the error codes in proto file, ErrorResponse is the underlying message depends on enum ErrorCode. I want ErrorResponse and base ErrorCode defines in one file that others can not edit. If others need new error code , they could define that on their own files.

But we cannot extend the enum.

@ObsidianMinor
Copy link
Contributor

What you could do is define a oneof that contains a normal ErrorCode and an int32 so that users could use the int32 for custom errors and ErrorCode for predefined errors. Then they could use their own casting or conversion systems.

message ErrorResponse {
    oneof code {
        ErrorCode error_code = 1;
        int32 custom_code = 2;
    }
}

Could this work?

@timestee
Copy link
Author

timestee commented May 7, 2019

@ObsidianMinor

Both have custom error code and predefined error code? Not a good choice i think, the custom error code may override the predefined one. What i want to do is keep some error code reserved(<1000 perhaps), and others are also defined in proto.

Here is my workaround now :

message ErrorResponse {
    int32 code = 1;
    string message = 2;
}
enum ErrorCode {
    OK = 0;
    UNKNOWN = 1;
}

Users could define other error code in another enum, like:

enum LogicErrorCode {
    USER_NOT_FOUND = 1001;
    DB_ERROR  = 1002;
}

Then users should call buildErrorResponse to construct new ErrorResponse.

func buildErrorResponse(code LogicErrorCode,msg string) *ErrorResponse{
	if msg == "" {
		msg = code.String()
	}
	return &ErrorResponse{Code:int32(code),Message:msg}
}

When do care about the error code on the peer, could handle it like this, fortunately, not very bad.

func onError(err *ErrorResponse) {
	if err.Code == int32(ErrorCode_OK){
	}
	if err.Code == int32(LogicErrorCode_USER_NOT_FOUND){
	}
}

@BSBandme BSBandme added the P3 label Jun 11, 2019
@BSBandme BSBandme assigned ghost Jun 11, 2019
@ghost
Copy link

ghost commented Jun 11, 2019

I think you can do this:

message ErrorResponse {
    ErrorCode code = 1;
    string message = 2;
    extensions 1000 to max;
}
enum ErrorCode {
    UNSPECIFIED = 0;
    OK = 1;
    CUSTOM = 2;
}

In the user's code, they can do:

message CustomErrorResponse {
  extend ErrorResponse {
    optional CustomErrorResponse custom_error_extension = 123456789;
  }
  enum LogicErrorCode {
    UNSPECIFIED = 0;
    USER_NOT_FOUND = 1;
    DB_ERROR  = 2;
  }
}

@ghost ghost closed this as completed Jun 11, 2019
@timestee
Copy link
Author

NOT A GOOG IDEA I THINK.

@simonjrichter
Copy link

I think the error codes are a valid use case for something like this -- I have generic errors for things the programmer did wrong, and component specific error codes for actual problems, e.g. reading from an SD Card I have success, out_of_range for when someone reads beyond the end of the device (they should know better), and removed for when someone unplugged the card (the client can't know, and this is also component specific).

Reusing the common error codes without a form of inheritance is difficult.

This issue was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants