php小编子墨为您介绍解决杜松子酒中的“标头已写入。想要用 400 覆盖状态代码 200”问题的方法。这个问题通常发生在使用PHP进行网页开发时,可能会导致网页无法正常加载。解决方法包括检查代码中的重复输出、清空缓冲区、检查服务器配置等。通过采取适当的措施,您可以轻松解决这个问题,确保您的网页能够正常运行。
问题内容
我正在尝试使用 Gin 框架独立于 HTTP 请求来计算报告,但如果尚未关闭,我也想将其返回到请求。以下代码片段有时可以正常工作,但有时会抛出错误“标头已写入。想要用 400 覆盖状态代码 200”。我找不到解决方案。
// router.go
reportRoute.POST("/query", func(c *gin.Context) {
reporter.ReportInChan <- c
}) // Unpublish report by id
//reporter
package reporter
import (
"fmt"
"github.com/gin-gonic/gin"
)
var (
ReportInChan = make(chan *gin.Context)
)
func Listener() {
for {
select {
case req := <-ReportInChan:
queryReports(req)
}
}
}
func queryReports(req *gin.Context) {
type ReqQuery struct {
QueryID uint `json:"query_id"`
Parameters map[string]any `json:"parameters"`
}
type Req struct {
ReportID uint `json:"report_id"`
Queries []ReqQuery `json:"queries"`
}
var reqBody Req
err := req.BindJSON(&reqBody)
if err != nil {
fmt.Println("hata var")
if ctx := req.Request.Context(); ctx.Done() == nil {
req.JSON(400, gin.H{"error": "Veriler Yanlış Gönderiliyor. Lütfen Bilgi İşlem Birimiyle İletişime Geçin ", "data": nil})
}
return
}
}
解决方法
下面的处理程序会将上下文发送到通道,然后返回。一旦处理程序返回,请求将被取消。此时,接收 Goroutine 可能根本没有机会产生任何输出,但有时可能会产生任何输出。如果接收 Goroutine 在 Gin 框架写入响应之后但在取消上下文之前开始生成输出,您将收到上述错误。
reportRoute.POST("/query", func(c *gin.Context) {
reporter.ReportInChan <- c
})
您真正需要做的是实现一个超时方案,因此如果请求处理程序可以在该超时之前响应,则将其写入输出并返回。否则,您让请求处理程序运行,并找到另一种方法将结果返回给调用者,可能是通过另一个 API 调用:
type reportRequest struct {
ReportParams
result chan ReportResult
}
reportRoute.POST("/query", func(c *gin.Context) {
req:=reportRequest {
ReportParams: {...},
result: make(chan ReportResult),
}
reporter.ReportInChan <- req
select {
case time.After(100*time.Millisecond):
// Wait 100 msecs
case result<-req.result:
// Write the result
}
})
上面的代码将从请求上下文创建一个报告请求,创建一个返回通道,然后将其发送到报告处理器。如果报表处理器在 100 毫秒内响应,则可以写入结果。否则,结果应存储在可以由另一个 API 检索的其他位置。
报表处理器应如下所示:
func (r Reporter) reportProcessor() {
for request:=range r.ReportInChan {
result:=processReport(request)
select {
case request.result <- result:
// Wrote the result
default:
// Cannot write the result, handler returned
storeResult(result)
}
}
以上就是如何解决杜松子酒中的“标头已写入。想要用 400 覆盖状态代码 200”的详细内容,更多请关注编程网其它相关文章!