【问题标题】:Retrieving data from GORM Raw() Query从 GORM Raw() 查询中检索数据
【发布时间】:2021-06-14 02:17:47
【问题描述】:

我正在尝试通过基于项目的学习来学习 Golang。我摆在自己面前的问题是模拟客户将产品添加到他们的购物车中。目前,我有 Cart.go 这样的模型..

type Cart struct {
     ID         string    
     Customer   Customer  
     CustomerID string    
     Product    Product   
     ProductID  string    
     CreatedAt  time.Time 
     UpdatedAt  time.Time
}

在购物车模型上,我有一个函数定义为

func (c *Cart) GetAllItemsInCart(db *gorm.DB, customer_id string) (*gorm.DB, error) {
    items := db.Raw("SELECT id, product_id FROM carts WHERE customer_id = ?", customer_id).Scan(&c)

    return items, nil
}

这个函数在控制器中调用

func (server *Server) GetAllCartItems(w http.ResponseWriter, r *http.Request) {
    vars := mux.Vars(r)

    id := vars["id"]

    cart := models.Cart{}

    items, err := cart.GetAllItemsInCart(server.DB, id)

    if err != nil {
        responses.ERROR(w, http.StatusInternalServerError, err)
        return
    }

    responses.JSON(w, http.StatusOK, items)
}

据我所知,目前Scan() 将扫描结构的值,或者在这种情况下将找到的数据加载到指定的结构中。但是,我看到的回复是

 {
    "Value": null,
    "Error": null,
    "RowsAffected": 2
 }

这给了我 50% 的希望,因为 "RowsAffected": 2 是正确的。但是,有效载荷响应显然不是我想要的。任何指导将不胜感激,谢谢。

【问题讨论】:

  • 使用Scan(c)c已经是一个指针了。

标签: go go-gorm


【解决方案1】:

Scan 将值放入指向您给它的变量的指针 (via &c),并返回一个数据库事务对象。您正在调用该事务对象items,但事实并非如此。商品(即购物车中的内容)在c *Cart 中,而不是在Scan 返回的东西中。

你的方法通过填充修改c,它不需要返回任何东西,除非你想返回Scan可能返回的错误。

而不是这个...

    items, err := cart.GetAllItemsInCart(server.DB, id)

    // ... 

    responses.JSON(w, http.StatusOK, items)

你应该这样做:

    err := cart.GetAllItemsInCart(server.DB, id)

    // ...

    responses.JSON(w, http.StatusOK, cart)

【讨论】:

  • 感谢您的帮助和洞察力,非常感谢!
【解决方案2】:

您需要解决一些问题:

  • 您需要使用Scan(c) 而不是Scan(&c),因为c 已经是一个指针。
  • 您应该始终检查错误。在您的 GetAllItemsInCart 方法中,您不会通过或检查错误。从技术上讲,您确实传递了它(在 items 对象内),但您没有在任何地方检查它。
  • 无需将*gorm.DB 指针向上传递。

如果您想以您已经开始的方式保留代码的结构,它可能看起来像这样:

func (c *Cart) GetAllItemsInCart(db *gorm.DB, customer_id string) error {
    return db.Raw("SELECT id, product_id FROM carts WHERE customer_id = ?", customer_id).Scan(c).Error
}

// controller
func (server *Server) GetAllCartItems(w http.ResponseWriter, r *http.Request) {
    vars := mux.Vars(r)

    id := vars["id"]

    cart := models.Cart{}

    err := cart.GetAllItemsInCart(server.DB, id)
    if err != nil {
        responses.ERROR(w, http.StatusInternalServerError, err)
        return
    }

    responses.JSON(w, http.StatusOK, cart)
}

【讨论】:

  • 感谢您的回复,非常感谢您的帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-12-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多