When php editor Baicao introduced the use of gRPC, he pointed out that if the specified value is false in the gRPC request, then gRPC will not return a Boolean value. This means that when using gRPC, we need to pay attention to how return values are handled to avoid confusion and errors. Understanding this detail will help us better understand and apply the functions of gRPC, and improve our programming efficiency and code quality. Let's delve into more features and usage of gRPC to bring better performance and scalability to our projects.
func (m *todoserver) gettodos(ctx context.context, empty *emptypb.empty) (*desc.gettodosresponse, error) { todos, err := m.todoservice.gettodos() if err != nil { return nil, err } todosresp := make([]*desc.gettodosresponse_todo, 0, len(todos)) for _, todo := range todos { todosresp = append(todosresp, &desc.gettodosresponse_todo{ id: todo.id, title: todo.title, iscompleted: todo.iscompleted, }) } return &desc.gettodosresponse{todos: todosresp}, nil }
service TodoService { rpc GetTodos(google.protobuf.Empty) returns (GetTodosResponse) {} } message GetTodosResponse { repeated Todo todos = 1; message Todo { int64 id = 1; string title = 2; bool is_completed = 3; } }
service TodoService { rpc GetTodos(google.protobuf.Empty) returns (GetTodosResponse) {} } message GetTodosResponse { repeated Todo todos = 1; message Todo { int64 id = 1; string title = 2; bool is_completed = 3; } }
I have a record in the database |Number |Title |Completed | |-|-|-| | 1 |Ahhh|False|
The above function returns{"todos": [{"id": "1", "title": "aaa"}]}
But once I changeis_completed
istrue
, the result is correct{"todos ": [{"id": "1", "title": "aaa", "iscompleted": true}]}
This is by design and to improve efficiency.
The "zero" value ofbool
isfalse
- so when aprotobuf
structure is initialized with afalse
value, when using the standard This field does not need to be explicitly declared when using the library'sencoding/json
unmarshaller. On the encoding side, if the field's json tag contains theomitempty
qualifier, the standard library'sencoding/json
marshaler will remove any zero values - this is what you see of. You will see the same behavior if thetitle
string field is""
(i.e. the zero value of the string).
View the generated code (*.pb.go
), thebool
field definition of the structure will be as follows:
type todo struct { // ... iscompleted bool `protobuf:"varint,5,opt,name=is_complete,proto3" json:"is_complete,omitempty"` }
Thusjson:"...,omitempty"
instructs theencoding/json
marshaler to omit any zero values during marshaling using these tags.
If you want to override this behavior:
omitempty
directive from the generated code (not recommended - due to the need to manage editing during the development life cycle). But if you must do this, seethis answer;grpc-gateway
, please override it at runtime, for examplegwmux := runtime.newservemux(runtime.withmarshaleroption(runtime.mimewildcard, &runtime.jsonpb{origname: true, emitdefaults: true}))
encoding/json
), use thejson
marshaler" in this package google.golang.org/protobuf/encoding/protojson"
:protojson.Marshaler{EmitDefaults: true}.Marshal(w, resp)
As mentioned inthis answer.
The above is the detailed content of gRPC does not return a boolean value if the value is false. For more information, please follow other related articles on the PHP Chinese website!