You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何覆盖Go net/http默认的404未找到请求处理器?

如何自定义Go http.ServeMux的404响应

你用"*"作为路由注册自定义404处理器不生效,核心原因是Go的http.ServeMux路由匹配规则里,通配符*只能作为路径前缀的尾部(比如/api/*),单独的*不会匹配任何请求路径,所以这个处理器永远不会被触发。

下面是两种可行的解决方法:

方法一:包装ServeMux实现自定义404

创建一个自定义Handler类型,包装原有的ServeMux,通过捕获响应状态码来判断是否需要返回自定义404:

package main

import (
    "net/http"
)

type customMux struct {
    mux *http.ServeMux
}

func (c *customMux) ServeHTTP(w http.ResponseWriter, r *http.Request) {
    // 用自定义ResponseRecorder捕获原ServeMux的响应状态
    rec := &responseRecorder{ResponseWriter: w, statusCode: http.StatusOK}
    c.mux.ServeHTTP(rec, r)
    
    // 如果原响应是404,替换为自定义内容
    if rec.statusCode == http.StatusNotFound {
        w.WriteHeader(http.StatusNotFound)
        w.Write([]byte("自定义404错误:请求的路径不存在"))
    }
}

// 自定义ResponseRecorder,用于捕获响应状态码
type responseRecorder struct {
    http.ResponseWriter
    statusCode int
}

func (r *responseRecorder) WriteHeader(code int) {
    r.statusCode = code
    r.ResponseWriter.WriteHeader(code)
}

func main() {
    api := http.NewServeMux()

    api.HandleFunc("/test", func(w http.ResponseWriter, r *http.Request) {
        w.WriteHeader(http.StatusOK)
        w.Write([]byte("test success"))
    })

    // 使用自定义的mux替代原ServeMux
    customHandler := &customMux{mux: api}
    
    err := http.ListenAndServe(":8080", customHandler)
    if err != nil {
        panic(err)
    }
}

方法二:利用最长匹配规则注册根路径处理器

http.ServeMux遵循最长路径匹配原则,注册一个"/"的处理器,只有当所有更具体的路径都不匹配时,才会触发这个根处理器,直接返回自定义404:

package main

import "net/http"

func main() {
    api := http.NewServeMux()

    api.HandleFunc("/test", func(w http.ResponseWriter, r *http.Request) {
        w.WriteHeader(http.StatusOK)
        w.Write([]byte("test success"))
    })

    // 注册根路径处理器,仅在无其他匹配时触发
    api.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
        // 可选:排除favicon.ico请求,避免不必要的404日志
        if r.URL.Path == "/favicon.ico" {
            http.NotFound(w, r)
            return
        }
        w.WriteHeader(http.StatusNotFound)
        w.Write([]byte("自定义404错误:请求的路径不存在"))
    })

    err := http.ListenAndServe(":8080", api)
    if err != nil {
        panic(err)
    }
}

内容的提问来源于stack exchange,提问作者baitendbidz

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 06:07:24