Go解析IAM Policy时JSON类型断言匹配异常问题求助
解决Go解析IAM Policy中Action字段的类型问题
问题根源
你遇到的type switch进入default分支,是因为json.Unmarshal处理JSON数组时,会将其解析为[]interface{}而非[]string,而你之前的判断逻辑可能只检查了string和[]string,导致数组类型匹配失败。
方案一:自定义Action类型实现UnmarshalJSON(推荐)
通过自定义类型并实现json.Unmarshaler接口,统一将单个字符串或字符串数组转为[]string,后续无需再做类型判断,代码更简洁易维护。
示例代码:
import ( "encoding/json" "fmt" ) type Policy struct { Statement []Statement `json:"Statement"` } type Statement struct { Action Action `json:"Action"` // 其他字段如Effect、Resource等按需定义 } // 自定义Action类型,底层是字符串数组 type Action []string // 实现UnmarshalJSON接口,处理单个字符串或数组两种情况 func (a *Action) UnmarshalJSON(data []byte) error { // 先尝试解析为单个字符串 var singleStr string if err := json.Unmarshal(data, &singleStr); err == nil { *a = []string{singleStr} return nil } // 尝试解析为字符串数组 var strArr []string if err := json.Unmarshal(data, &strArr); err == nil { *a = strArr return nil } return fmt.Errorf("invalid Action format: %s", data) }
使用时直接遍历stmt.Action即可,它已经是[]string类型,无需额外类型转换。
方案二:调整type switch逻辑匹配[]interface{}
如果不想自定义类型,可以修改type switch的判断逻辑,直接处理json.Unmarshal生成的[]interface{}类型,再逐个转换为字符串。
示例代码:
// 假设Statement结构体中Action定义为interface{} type Statement struct { Action interface{} `json:"Action"` // 其他字段... } // 遍历Statement时处理Action for _, stmt := range policy.Statement { switch actionVal := stmt.Action.(type) { case string: // 处理单个字符串场景 actions := []string{actionVal} // 你的业务逻辑... case []interface{}: // 处理数组场景,逐个转换为string actions := make([]string, len(actionVal)) for i, val := range actionVal { strVal, ok := val.(string) if !ok { // 处理非字符串元素的错误情况 panic(fmt.Sprintf("Action element is not string: %v", val)) } actions[i] = strVal } // 你的业务逻辑... default: // 处理无效类型 panic(fmt.Sprintf("unsupported Action type: %T", actionVal)) } }
这种方法无需修改结构体定义,但每次处理都要做类型转换,代码相对繁琐。
内容的提问来源于stack exchange,提问作者eugercek
相关产品推荐
相关产品推荐

