Wynik MongoDB find()
to zawsze lista dokumentów. Więc jeśli chcesz otrzymać listę wartości, musisz przekonwertować ją ręcznie, tak jak to zrobiłeś.
Korzystanie z niestandardowego typu (pochodzącego z string
)
Pamiętaj też, że jeśli utworzysz własny typ (pochodzący z string
), możesz nadpisać jego logikę unmarshaling i „wyodrębnić” tylko username
z dokumentu.
Tak mogłoby to wyglądać:
type Username string
func (u *Username) SetBSON(raw bson.Raw) (err error) {
doc := bson.M{}
if err = raw.Unmarshal(&doc); err != nil {
return
}
*u = Username(doc["username"].(string))
return
}
A następnie zapytanie o nazwy użytkowników w wycinku:
c := mongodb.DB("mybase").C("mycollection") // Obtain collection
var uns []Username
err = c.Find(nil).Select(bson.M{"username": 1, "_id": 0}).All(&uns)
if err != nil {
fmt.Println(err)
}
fmt.Println(uns)
Zauważ, że []Username
to nie to samo co []string
, więc to może Ci wystarczyć, ale nie musi. Jeśli potrzebujesz nazwy użytkownika jako wartości string
zamiast Username
podczas przetwarzania wyniku możesz po prostu przekonwertować Username
do string
.
Korzystanie z Query.Iter()
Innym sposobem uniknięcia kopiowania wycinków byłoby wywołanie Query.Iter()
, przeprowadź iterację wyników i wyodrębnij i zapisz username
ręcznie, podobnie jak powyższa niestandardowa logika unmarshalingu.
Tak mogłoby to wyglądać:
var uns []string
it := c.Find(nil).Select(bson.M{"username": 1, "_id": 0}).Iter()
defer it.Close()
for doc := (bson.M{}); it.Next(&doc); {
uns = append(uns, doc["username"].(string))
}
if err := it.Err(); err != nil {
fmt.Println(err)
}
fmt.Println(uns)