Description
The binding:"required" tag does not seem to work to require a nested object in the json body.
I have not been able to find documentation that show this is the expected behavior.
How to reproduce
package main
import (
"fmt"
"github.com/gin-gonic/gin"
)
type Nested struct {
Hello string `json:"hello"`
}
type TransferCreateBody struct {
TestNested Nested `json:"nested" binding:"required"`
TestNotNested string `json:"not_nested" binding:"required"`
}
func main() {
g := gin.Default()
g.POST("/hello", func(c *gin.Context) {
var req TransferCreateBody
if err := c.ShouldBindJSON(&req); err != nil {
fmt.Println(err)
c.JSON(400, gin.H{"error": err.Error()})
return
}
c.JSON(200, gin.H{"hello": req.TestNested.Hello})
})
g.Run(":9000")
}
For instance, a POST with body
{
"not_nested": "test"
}
does not return an error even though the "nested" parameter is missing.
Expectations
curl -X POST http://localhost:9000/hello
-H "Content-Type: application/json"
-d '{"not_nested": "test"}'
expects an error because the "nested" tag is not present
Actual result
The request returns a 200 status. (if the "not_nested" parameter is absent, the server returns a 400 status as expected)
Environment
- go version: 1.22.0
- gin version (or commit ref): 1.9.1
- operating system: mac OS 13.6.3
Comment From: jamesstocktonj1
This has been answered before here and you can fix it by making it a pointer as followed:
type TransferCreateBody struct {
TestNested *Nested `json:"nested" binding:"required"`
TestNotNested string `json:"not_nested" binding:"required"`
}
This results in a 400 response and {"error":"Key: 'TransferCreateBody.TestNested' Error:Field validation for 'TestNested' failed on the 'required' tag"}
Comment From: Pascal-Delange
Well, I stand corrected. Sorry for the duplicate post. However, if I may say, it's really hard to find documentation on how this is supposed to work :-) (in particular the other linked issues relating to the same question all seem to concern zero values of strings/ints, with the context I now understand it's the same cause, but without having the proper context it's not immediately obvious to search for it). Anyway, thanks for the answer !
Comment From: Pascal-Delange
well, while I'm at it, I posted a recap of the solution on stack overflow. Hope this can help others. https://stackoverflow.com/questions/78205172/go-gin-required-binding-seems-not-to-work-for-nested-structs/78205173#78205173