gtsocial-umbx

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README | LICENSE

status.go (4549B)


      1 /*
      2  *
      3  * Copyright 2017 gRPC authors.
      4  *
      5  * Licensed under the Apache License, Version 2.0 (the "License");
      6  * you may not use this file except in compliance with the License.
      7  * You may obtain a copy of the License at
      8  *
      9  *     http://www.apache.org/licenses/LICENSE-2.0
     10  *
     11  * Unless required by applicable law or agreed to in writing, software
     12  * distributed under the License is distributed on an "AS IS" BASIS,
     13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14  * See the License for the specific language governing permissions and
     15  * limitations under the License.
     16  *
     17  */
     18 
     19 // Package status implements errors returned by gRPC.  These errors are
     20 // serialized and transmitted on the wire between server and client, and allow
     21 // for additional data to be transmitted via the Details field in the status
     22 // proto.  gRPC service handlers should return an error created by this
     23 // package, and gRPC clients should expect a corresponding error to be
     24 // returned from the RPC call.
     25 //
     26 // This package upholds the invariants that a non-nil error may not
     27 // contain an OK code, and an OK code must result in a nil error.
     28 package status
     29 
     30 import (
     31 	"context"
     32 	"errors"
     33 	"fmt"
     34 
     35 	spb "google.golang.org/genproto/googleapis/rpc/status"
     36 
     37 	"google.golang.org/grpc/codes"
     38 	"google.golang.org/grpc/internal/status"
     39 )
     40 
     41 // Status references google.golang.org/grpc/internal/status. It represents an
     42 // RPC status code, message, and details.  It is immutable and should be
     43 // created with New, Newf, or FromProto.
     44 // https://godoc.org/google.golang.org/grpc/internal/status
     45 type Status = status.Status
     46 
     47 // New returns a Status representing c and msg.
     48 func New(c codes.Code, msg string) *Status {
     49 	return status.New(c, msg)
     50 }
     51 
     52 // Newf returns New(c, fmt.Sprintf(format, a...)).
     53 func Newf(c codes.Code, format string, a ...interface{}) *Status {
     54 	return New(c, fmt.Sprintf(format, a...))
     55 }
     56 
     57 // Error returns an error representing c and msg.  If c is OK, returns nil.
     58 func Error(c codes.Code, msg string) error {
     59 	return New(c, msg).Err()
     60 }
     61 
     62 // Errorf returns Error(c, fmt.Sprintf(format, a...)).
     63 func Errorf(c codes.Code, format string, a ...interface{}) error {
     64 	return Error(c, fmt.Sprintf(format, a...))
     65 }
     66 
     67 // ErrorProto returns an error representing s.  If s.Code is OK, returns nil.
     68 func ErrorProto(s *spb.Status) error {
     69 	return FromProto(s).Err()
     70 }
     71 
     72 // FromProto returns a Status representing s.
     73 func FromProto(s *spb.Status) *Status {
     74 	return status.FromProto(s)
     75 }
     76 
     77 // FromError returns a Status representation of err.
     78 //
     79 //   - If err was produced by this package or implements the method `GRPCStatus()
     80 //     *Status`, or if err wraps a type satisfying this, the appropriate Status is
     81 //     returned.  For wrapped errors, the message returned contains the entire
     82 //     err.Error() text and not just the wrapped status.
     83 //
     84 //   - If err is nil, a Status is returned with codes.OK and no message.
     85 //
     86 //   - Otherwise, err is an error not compatible with this package.  In this
     87 //     case, a Status is returned with codes.Unknown and err's Error() message,
     88 //     and ok is false.
     89 func FromError(err error) (s *Status, ok bool) {
     90 	if err == nil {
     91 		return nil, true
     92 	}
     93 	type grpcstatus interface{ GRPCStatus() *Status }
     94 	if gs, ok := err.(grpcstatus); ok {
     95 		return gs.GRPCStatus(), true
     96 	}
     97 	var gs grpcstatus
     98 	if errors.As(err, &gs) {
     99 		p := gs.GRPCStatus().Proto()
    100 		p.Message = err.Error()
    101 		return status.FromProto(p), true
    102 	}
    103 	return New(codes.Unknown, err.Error()), false
    104 }
    105 
    106 // Convert is a convenience function which removes the need to handle the
    107 // boolean return value from FromError.
    108 func Convert(err error) *Status {
    109 	s, _ := FromError(err)
    110 	return s
    111 }
    112 
    113 // Code returns the Code of the error if it is a Status error or if it wraps a
    114 // Status error. If that is not the case, it returns codes.OK if err is nil, or
    115 // codes.Unknown otherwise.
    116 func Code(err error) codes.Code {
    117 	// Don't use FromError to avoid allocation of OK status.
    118 	if err == nil {
    119 		return codes.OK
    120 	}
    121 
    122 	return Convert(err).Code()
    123 }
    124 
    125 // FromContextError converts a context error or wrapped context error into a
    126 // Status.  It returns a Status with codes.OK if err is nil, or a Status with
    127 // codes.Unknown if err is non-nil and not a context error.
    128 func FromContextError(err error) *Status {
    129 	if err == nil {
    130 		return nil
    131 	}
    132 	if errors.Is(err, context.DeadlineExceeded) {
    133 		return New(codes.DeadlineExceeded, err.Error())
    134 	}
    135 	if errors.Is(err, context.Canceled) {
    136 		return New(codes.Canceled, err.Error())
    137 	}
    138 	return New(codes.Unknown, err.Error())
    139 }