Go开发Twitter克隆查询关注者推文触发nil pointer dereference panic求助
问题根源
你的空指针panic由以下三个代码疏漏共同导致:
- 调用MongoDB
Aggregate方法后没有检查返回错误,一旦聚合执行失败,返回的cursor就是nil,后续调用cursor.All时会直接触发空指针引用,和你给出的报错堆栈完全匹配:go.mongodb.org/mongo-driver/mongo.(*Cursor).All(0x0, ...)中的0x0就代表此时cursor是空指针。 - 聚合语句中的排序字段写错:
$lookup关联出来的推文存放在tweets字段下,$unwind后需要排序的字段是tweets.date而非根路径下的date,这个错误会直接导致Aggregate执行失败返回nil cursor。 - 同作用域下重复声明
err变量:你先通过cursor, err := col.Aggregate(...)声明了err,后续又用err := cursor.All(...)重复声明,会覆盖上层的错误信息,导致你无法捕获到Aggregate的执行错误。
修复后的db包代码
package db import ( "context" "time" "fmt" "github.com/JeffersonGarcia15/Twitter-Clone/models" "go.mongodb.org/mongo-driver/bson" ) /* ReadFollowersTweets 读取我关注的用户发布的推文 */ func ReadFollowersTweets(ID string, page int) ([]models.ReturnFollowersTweets, bool) { ctx, cancel := context.WithTimeout(context.Background(), 15*time.Second) defer cancel() db := MongoCN.Database("twitter") col := db.Collection("joins") skip := (page - 1) * 20 conditions := make([]bson.M, 0) conditions = append(conditions, bson.M{"$match": bson.M{"userid": ID}}) conditions = append(conditions, bson.M{ "$lookup": bson.M{ "from": "tweets", "localField": "userrelationid", "foreignField": "userid", "as": "tweets", }}) conditions = append(conditions, bson.M{"$unwind": "$tweets"}) // 让同一页的所有推文都采用统一结构输出 // 修复排序字段路径,MongoDB排序用数值-1代表降序,不要用字符串desc conditions = append(conditions, bson.M{"$sort": bson.M{"tweets.date": -1}}) conditions = append(conditions, bson.M{"$skip": skip}) conditions = append(conditions, bson.M{"$limit": 20}) cursor, err := col.Aggregate(ctx, conditions) // 新增Aggregate错误检查,避免拿到nil cursor if err != nil { fmt.Println("聚合查询失败:", err.Error()) return nil, false } var result []models.ReturnFollowersTweets // 去掉重复的短声明,直接复用之前的err变量 err = cursor.All(ctx, &result) if err != nil { fmt.Println("读取游标失败:", err.Error()) return result, false } return result, true }
额外优化建议
路由层中返回成功状态码用http.StatusCreated(201)不符合RESTful规范,读取类接口成功应该返回http.StatusOK(200)。
内容的提问来源于stack exchange,提问作者Adilson Jurado
相关产品推荐
相关产品推荐

