网站建设方案报价表,国外代理ip,网站seo 优帮云,网上培训场景
最近笔者在研究web框架过程中#xff0c;发现了一个响应类型的问题#xff0c;困扰许久#xff0c;原因就是设置了响应状态码后#xff0c;然后设置响应类型为application/json。在实际请求后#xff0c;响应类型变成了text/plain; charsetutf-8格式。 问题解决发现了一个响应类型的问题困扰许久原因就是设置了响应状态码后然后设置响应类型为application/json。在实际请求后响应类型变成了text/plain; charsetutf-8格式。 问题解决 先设置请求头的Content-type属性再设置响应状态码即可解决问题 // 例如
func writeContentType(w http.ResponseWriter) {header : w.Header()if val : header[Content-Type]; len(val) 0 {header[Content-Type] []string{application/json; charsetutf-8}}
}
// 先执行
writeContentType(w)
// 再执行
w.WriteHeader(code)分析导致问题的原因
我们处理请求接收的参数是http.ResponseWriter类型的它是一个接口类型只要实现了这个接口都可以作为参数传递进来。
而实际传递进来的是response结构体它实现了http.ResponseWriter接口 可以通过定位http.ResponseWriter结构体在同文件里面找到response结构体 我们查看一下response结构体的WriteHeader方法的源码里面有一段代码
func (w *response) WriteHeader(code int) {// 忽略代码if w.calledHeader w.cw.header nil {w.cw.header w.handlerHeader.Clone()}// 忽略代码
} 再看一下response结构体的Header方法因为我们实际就是调用它然后设置响应头的
func (w *response) Header() Header {if w.cw.header nil w.wroteHeader !w.cw.wroteHeader {w.cw.header w.handlerHeader.Clone()}w.calledHeader truereturn w.handlerHeader
}总结问题
通过分析上面两组代码可以发现如果我们先执行了WriteHeader方法它会给w.cw.header设置值此时我们再调用Header方法设置Content-type属性时经过if判断w.cw.header并不等于nil了所以我们给header设置的属性无法设置到w.cw.header上面导致实际响应时content-type发生变化。关键点就在于w.cw.header这个字段如果设置的属性没到它上面的话会导致失效。