2016-02-05 93 views
1

我正在跟进Golang Decoding Generic JSON Objects to One of Many Formats作为解组泛型json的一种方式。我将会有许多不同类型的tho可以被其他人添加,所以硬编码的case语句是不可行的。使用类型查找映射反编组泛型json

我也不想将该类型硬编码为字符串,但让那些使用库的人选择“查找”名称,以防他们稍后重新命名其基础结构。

我基本上是在寻找这样的事情:

type myInterface interface { 
    Something() // irrelevant, just to show you It's not about interface{} 
} 

type myBar struct {}  // fulfils myInterface 
type mySomething struct {} // fulfils myInterface 

var types = make(map[string]type) // <--- Obvious Pseudo code ;) 
types["foo:bar"] = myBar  // done by whoever uses the library 
types["1230988"] = mySomething // ... 

type storageWrapper struct { 
    Type string 
    Data json.RawMessage 
} 

func loadSomething(id string) myInterface { 
    buf := db.load(id) // pseudo code but you get the idea 
    sw := &storageWrapper{} 
    json.Unmarshal(buf, sw) 

    // now the interesting part 
    targetType := types[sw.Type] 
    thing := &targetType{} 
    json.Unmarshal(sw.Data, thing) 
    return thing 
} 

我有这种感觉,我的得太多整个问题。或者,我正试图弯曲与其底层哲学冲突的事物。我非常开放并且非常感谢任何意见,建议采取不同的方法来解决整个问题

回答

0

typesmap[string]myInterface,并且要注册一个类型,请调用者将该类型的空值(不是引用)存储到地图。然后,为了解组,可以通过将空值从映射中复制出来,解组并将其返回(或引用它)来“获取类型”。界面值将完成识别需要哪种类型的工作。此外,如果用户想要将某些字段默认为非零/空值(如果它们未在JSON中提供),则实际上可以通过将这些值存储在类型映射中的结构中来实现。

+0

接受这个答案是因为它完成了工作。不过,我现在改变了我的代码,所以它不再依赖于类型映射 – paukul