lundi 26 février 2018

How to use a reflect.Type to perform a type assertion

I know reflection is generally frowned upon in go but for my current purposes Im pretty sure it is the best solution.

Essentially my project is cli tool which will output an xml query based on incoming commands and return the corresponding result.

There is some boiler plate code for each command request where default values are populated and supplied values validated.

So I have a series of Command objects based on a Command struct as follows:

type Command struct {
    Name        string
    Request     interface{}
    RequestType reflect.Type
    Response    interface{}

    RegisterFunc func(parentCmd *cobra.Command, cmd *Command) error
}

For the most part I really don't care about the types of the request/response (just xml encode/decode). However I need to briefly cast it to a concrete type to validate with struct annotations So for example I might do something like this:

 var set bool
    if ccReq, set = command.Request.(*CreateCredentialRequest); !set {
        log.Fatal(errors.New("invalid request type"))
    }

    result, err := govalidator.ValidateStruct(ccReq)
    if err != nil {
        println("error: " + err.Error())
        os.Exit(1)
    }

However in an ideal would I would like to handle this generically for all commands, something like this:

var set bool
    if ccReq, set = command.Request.(command.RequestType); !set {
        log.Fatal(errors.New("invalid request type"))
    }

However this results in the error:

command.RequestType is not a type

So, how can I store the value of a type for a later type assertion





Aucun commentaire:

Enregistrer un commentaire