[zeromicro/go-zero][BUG] HTTP form 解析误报错

2024-02-18 162 views
8
一、问题描述

HTTP form 方式提交时,框架解析参数会误报 field %s is not set

二、复现步骤

使用以下 api 文件,通过 goctl 生成项目

type UploadRequest {
    Name string `json:"name" form:"name"`
    Desc string `json:"desc,optional" form:"desc,optional"`
    File string `json:"file,optional" form:"file,optional"`
}

type UploadResponse {
    Code    int32  `json:"code" form:"code"`
    Message string `json:"message" form:"message"`
}

service upload {
    @handler upload
    post /api/v1/upload (UploadRequest) returns (UploadResponse)
}

通过 curl 命令请求:

curl -X "POST" "http://127.0.0.1:8888/api/v1/upload" \
     -H 'Content-Type: application/x-www-form-urlencoded; charset=utf-8' \
     --data-urlencode "name=test.png" \
     --data-urlencode "desc=测试文件" \
     --data-urlencode "file=aaaaa"

此时框架将会返回错误信息: field name is not set,事实上数据已经传入,此时只需要将 name 设置为 optional 即可缓解此问题。

⚠️注意: 使用 optional 后可以缓解这个问题,逻辑层仍能拿到正确的值。

@kevwan

回答

0

如果以Content-Type: application/x-www-form-urlencoded; charset=utf-8这种类型传递请求body,在api文件中需要将tag定义为form:"xxx"形式,参数解析只读第一个tag,不支持多tag形式,因此正确定义为:

type UploadRequest {
    Name string `form:"name"`
    Desc string `form:"desc,optional"`
    File string `form:"file,optional"`
}

type UploadResponse {
    Code    int32  `form:"code"`
    Message string `form:"message"`
}
....
7

@anqiansong 也就是说在多 tag (json:"name" form:"name") 的情况下,go-zero 仅读取第一个 json tag,然后尝试通过 json 形式获取 body 里的数据么?

6

保持单一,不要同一个放在多个部分。

7

我试了path可以拿到第一个参数,后面的拿不到,改json,from,都报错:field xx is not set