I was using pipe function in mgo to retrieve data. My data structs are as follows.
type Company struct {
Id bson.ObjectId `bson:"_id,omitempty"`
CompanyName string
Slug string
CompanyUsers []CompanyUser
}
type CompanyUser struct {
UserName string
Email string
FullName string
}
I needed to check whether a given "UserName" is present under "CompanyUsers" in a "Company" with a given "Slug".
Both Slug and UserName are provided by the User.
Using Pipe function I successfully done the search, but the data is returned with an empty CompanyUsers array.
My query is as follows:
var companyResults []Company
pipeline := []bson.M{
{"$match": bson.M{"slug": slug}},
{"$unwind": "$companyusers"},
{"$match": bson.M{
"companyusers.username": username,
}},
}
err := c.Pipe(pipeline).All(&companyResults)
This provides me a search result as follows:
[{ObjectIdHex("573aa0fddd731711c94830ca") MyCompany companyslug [] }]
None of the data in CompanyUsers are retrieved. How can I solve this error?
Try making companyResults
a []map[string]interface{}
instead of a []Company
to see what sort of a result you get. This helps to figure out what the structure of companyResults
should be.
var companyResults []map[string]interface{}
You will see a result like,
[map[companyname:MyCompany slug:companyslug companyusers:map[username:username] _id:test]]
See that companyusers
is infact a map not an array. This is because your usage of the $unwind
stage. It deconstructs the array, outputting one document for each element in the array. See docs.
I agree with John Smith's answer, that you do not need pipelines at all. But following should give you the desired result.
type Result struct {
Id string `bson:"_id,omitempty"`
CompanyName string
Slug string
CompanyUsers CompanyUser
}
var companyResults []Result
I might be missing something, but why do you need Pipe
for this?
You probably could do it easier:
query := bson.M{"slug": slug, "companyusers.username": username}
err := c.Find(query).All(&companyResults)
I'm fairly certain this would give you the same results.
However, the main problem is you didn't give the bson marshaller the fields name. Since the field in your database is companyusers
and username
you'll have to tell that to the marshaller.
type Company struct {
Id bson.ObjectId `bson:"_id,omitempty"`
CompanyName string
Slug string
CompanyUsers []CompanyUser `bson:"companyuser"`
}
type CompanyUser struct {
UserName string `bson:"username"`
Email string
FullName string
}
You probably want to fix that for the rest of the fields as well.