Problem receiving Axios post data from reactjs app using Golang

huangapple go评论83阅读模式
英文:

Problem receiving Axios post data from reactjs app using Golang

问题

我有一个使用ReactJS托管的本地网页,它通过Axios在9000端口发送POST请求。我有一个Golang服务器监听该端口并接收该POST请求。然后,它解码该请求,但是却无法获取其中的任何数据。以下是在ReactJS应用程序中发送Axios POST请求的代码部分。

    onSubmit = (event) => {
        event.preventDefault();
        let { task } = this.state;
        console.log("printing new task title:", task);
        if (task) {
            axios
            .post(
                endpoint + "/api/task",
                {task},
                {headers: {"Content-Type": "application/x-www-form-urlencoded"}}
            )
            .then((res) => {
                this.getTasks();
                this.setState({task: ""});
                console.log(res);
            });
        }
    };

以下是处理该POST请求的Golang服务器代码部分。

// CreateTask create task route
func CreateTask(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Context-Type", "application/x-www-form-urlencoded")
    w.Header().Set("Access-Control-Allow-Origin", "*")
    w.Header().Set("Access-Control-Allow-Methods", "POST")
    w.Header().Set("Access-Control-Allow-Headers", "Content-Type")
    var newTask listItem
    _ = json.NewDecoder(r.Body).Decode(&newTask)
    fmt.Println(newTask)
    insertOneTask(newTask)
    json.NewEncoder(w).Encode(newTask)
}

以下是listItem结构体的定义。

type listItem struct {
    ID        primitive.ObjectID `json:"_id,omitempty" bson:"_id,omitempty"`
    Title     string             `json:"title,omitempty"`
    Completed bool               `json:"completed,omitempty"`
}

我尝试将其重命名为title而不是task,并且只传递静态变量,但都没有成功。

在控制台中,它正确地打印出输入的文本,但是当控制台输出来自Golang服务器的axios响应时,其响应从不包含任务名称。

以下是来自Golang服务器响应的数据部分的示例:data: {_id: '000000000000000000000000', title:'Test'}

它只输出data: {_id: '000000000000000000000000'}

在接收到POST请求后,Golang终端的输出如下所示:

{ObjectID("000000000000000000000000") false}
Inserted a Single Record  ObjectID("63decde2a336b8e7cdc2b865")

似乎新任务的task属性被列为''。我的问题是新任务没有来自网页的输入文本。如果您需要更多代码,请参考以下链接:

英文:

I have a locally hosted webpage using reactjs that sends an Axios post to port 9000. I have a Golang server listening to that port and it recieves the post. It then decodes the post but never gets any of its data. Below is the portion of code that sends the axios post in the reactjs app.

    onSubmit = (event) => {
        event.preventDefault();
        let { task } = this.state;
        console.log("printing new task title:", task);
        if (task) {
            axios
            .post(
                endpoint + "/api/task",
                {task},
                {headers: {"Content-Type": "application/x-www-form-urlencoded"}}
            )
            .then((res) => {
                this.getTasks();
                this.setState({task: ""});
                console.log(res);
            });
        }
    };

The below is the portion of the golang server that handles the post.

// CreateTask create task route
func CreateTask(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Context-Type", "application/x-www-form-urlencoded")
    w.Header().Set("Access-Control-Allow-Origin", "*")
    w.Header().Set("Access-Control-Allow-Methods", "POST")
    w.Header().Set("Access-Control-Allow-Headers", "Content-Type")
    var newTask listItem
    _ = json.NewDecoder(r.Body).Decode(&newTask)
    fmt.Println(newTask)
    insertOneTask(newTask)
    json.NewEncoder(w).Encode(newTask)
}

Below is the listItem struct

type listItem struct {
ID        primitive.ObjectID `json:"_id,omitempty" bson:"_id,omitempty"`
Title     string             `json:"title,omitempty"`
Completed bool               `json:"completed,omitempty"`
}

I've tried renaming it to title instead of task, and just passing in a static variable but to no avail.

In the console it correctly prints the inputed text, but when the console outputs the axios response from the golang server, its response never includes the task name.

This is an example of what the data portion of the response from the golang server should look like: data: {_id: '000000000000000000000000', title:'Test'}.

It only ever outputs this data: {_id: '000000000000000000000000'}

The golang terminal output after the post is recieved is as follows:

{ObjectID("000000000000000000000000")  false}
Inserted a Single Record  ObjectID("63decde2a336b8e7cdc2b865")

It seems the task attribute is listed as '' in the new . My problem is the new task doesn't have the inputted text from the webpage. If you need more of the code it's below

答案1

得分: 1

建议使用DevTools来调试这种问题。

截图显示payload是form-url-encoded格式。但是服务器尝试使用json解码器(_ = json.NewDecoder(r.Body).Decode(&newTask))来读取它。如果不忽略Decode的错误,它应该会报告内容不是有效的json。要解决此问题,只需从client/src/To-Do-List.js中删除{headers: {"Content-Type": "application/x-www-form-urlencoded"}}

更改后,payload将变为:

其他错误:

1. Context-Type头与响应中的内容不匹配

go-server/main.go中的CreateTask函数还有另一个问题。响应被编码为json:

json.NewEncoder(w).Encode(newTask)

这与以下代码冲突:

	w.Header().Set("Context-Type", "application/x-www-form-urlencoded")

应将头替换为:

	w.Header().Set("Context-Type", "application/json")

2. CORS设置不正确

	r.HandleFunc("/api/task", GetAllTasks).Methods("GET", "OPTIONS")
	r.HandleFunc("/api/task", CreateTask).Methods("POST", "OPTIONS")

OPTIONS请求将由GetAllTasks处理。为了允许POST请求中的Content-Type头,应将以下行添加到GetAllTasks中:

	w.Header().Set("Access-Control-Allow-Headers", "Content-Type")

由于CreateTask不处理OPTIONS请求,因此可以删除以下行:

	w.Header().Set("Access-Control-Allow-Origin", "*")
	w.Header().Set("Access-Control-Allow-Methods", "POST")
	w.Header().Set("Access-Control-Allow-Headers", "Content-Type")
英文:

It's recommended to use DevTools to debug such kind of problem.

The screenshot shows that the payload is form-url-encoded. But the server tries to read it with a json decoder (_ = json.NewDecoder(r.Body).Decode(&newTask)). If you do not ignore the error from Decode, it should report that the content is not a valid json. To fix the issue, just remove {headers: {"Content-Type": "application/x-www-form-urlencoded"}} from client/src/To-Do-List.js.

Problem receiving Axios post data from reactjs app using Golang

After the change, the payload will be:

Problem receiving Axios post data from reactjs app using Golang


Other errors:

1. Context-Type header does not match the content in the response

The func CreateTask in go-server/main.go has another issue too. The response is encoded as json:

json.NewEncoder(w).Encode(newTask)

Which conflicts with:

	w.Header().Set("Context-Type", "application/x-www-form-urlencoded")

The header should be replaced with:

	w.Header().Set("Context-Type", "application/json")

2. The CORS is not set correctly

	r.HandleFunc("/api/task", GetAllTasks).Methods("GET", "OPTIONS")
	r.HandleFunc("/api/task", CreateTask).Methods("POST", "OPTIONS")

The OPTIONS requests will be handled by GetAllTasks. In order to allow the Content-Type header in the POST request, the following line should be added to GetAllTasks:

	w.Header().Set("Access-Control-Allow-Headers", "Content-Type")

And since CreateTask does not handle the OPTIONS request, the following lines can be removed:

	w.Header().Set("Access-Control-Allow-Origin", "*")
	w.Header().Set("Access-Control-Allow-Methods", "POST")
	w.Header().Set("Access-Control-Allow-Headers", "Content-Type")

huangapple
  • 本文由 发表于 2023年2月5日 06:19:22
  • 转载请务必保留本文链接:https://go.coder-hub.com/75348748.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定