非导出类型的类型声明

I am using a 3rd party package, which allows you to create structures of a certain non-exported type through an exported function.

package squirrel

type expr struct {
    sql string
    args []interface{}
}

func Expr(sql string, args ...interface{}) expr {
    return expr{sql: sql, args: args}
}

Because of the way some other function of this library accepts data, I ended up with such a map:

m := map[string]interface{} {
    "col1": 123,
    "col2": "a_string",
    "col3": Expr("now()"),
}

but because of a different function in this library I need to filter out all squirrel.expr from this map.

Obviously, I wasn't able to assert the type directly, by doing so:

filtered := make(map[string]interface{})
for k, v := range m {
    switch v.(type) {
    case squirrel.expr:
        continue
    default:
        filtered[k] = v
    }
}

Is there another way to achieve the same result?

You may use reflection to compare the type of values to the type of squirrel.expr. Type here means the reflect.Type descriptors, acquired by reflect.TypeOf().

For example:

m := map[string]interface{}{
    "col1": 123,
    "col2": "a_string",
    "col3": squirrel.Expr("now()"),
}
fmt.Println(m)

exprType := reflect.TypeOf(squirrel.Expr(""))

filtered := make(map[string]interface{})
for k, v := range m {
    if reflect.TypeOf(v) == exprType {
        continue
    }
    filtered[k] = v
}
fmt.Println(filtered)

This will output:

map[col1:123 col2:a_string col3:{now() []}]
map[col1:123 col2:a_string]

Note:

We obtained the reflect.Type descriptor of the values we want to filter out by passing the return value of a squirrel.Expr() call (which is of type squirrel.expr). This is fine in this case, but if it is unfeasible to call this function just to get the type (e.g. the call has side effects which must be avoided), we can avoid that. We can use reflection to obtain the reflect.Type descriptor of the squirrel.Expr function itself, and get the type descriptor of its return type. This is how it could be done:

exprType := reflect.TypeOf(squirrel.Expr).Out(0)