grpc / grpc-go

The Go language implementation of gRPC. HTTP/2 based RPC

Home Page:https://grpc.io

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

How to modify the returned metadata

baozi-2019 opened this issue · comments

I want to add error message to returned metadata,but it does not work.This is my code.

func ErrorServerInterceptor(ctx context.Context, req any, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (resp any, err error) {
	resp, err = handler(ctx, req)
	if err != nil {
		data := make(map[string]string)
		data["exceptionResult"] = err.Error()
		errorMessage := &grpc_message.ErrorMessage{
			ServiceName: ServiceName,
			Reason:      err.Error(),
			Metadata:    data,
		}
		//incomingContext, _ := metadata.FromIncomingContext(ctx)
		bytes, _ := json.Marshal(errorMessage)
		md, ok := metadata.FromOutgoingContext(ctx)
		if !ok {
			md = metadata.New(map[string]string{})
		}
		md.Append("custom-key", string(bytes))
		ctx = metadata.NewOutgoingContext(ctx, md)
		return nil, nil
	}
	return resp, err
}

@aranjans you can assign it to me

@baozi-2019 could you provide more context on why you are not returning the error (returning nil) from your interceptor?

@baozi-2019 you need to return a non-nil error otherwise the client will not receive any explicit indication of success or failure for the RPC call, and the associated context modifications made by the interceptor may not be observable by the client.

In order to add metadata to context from Unary RPC server, you can use grpc.SetTrailer function. Consider using the example in https://github.com/grpc/grpc-go/blob/master/examples/features/metadata/server/main.go#L55-L56

Having said that, metadata.FromOutgoingContext(ctx) doesn't work on server, you need to use metadata.FromIncomingContext(ctx) to read metadata by the client. Refer documentation for sending and receiving metadata https://github.com/grpc/grpc-go/blob/master/Documentation/grpc-metadata.md#sending-and-receiving-metadata---server-side