ccm,ocm,ssmapi: fix HTTP/2 over TLS with h2c handler

aTLS.NewListener returns *LazyConn, not *tls.Conn, so Go's
http.Server cannot detect TLS via type assertion and falls back
to HTTP/1.x. When ALPN negotiates h2, the client sends HTTP/2
frames that the server fails to parse, causing HTTP 520 errors
behind Cloudflare.

Wrap HTTP handlers with h2c.NewHandler to intercept the HTTP/2
client preface and dispatch to http2.Server.ServeConn, consistent
with DERP, v2rayhttp, naive, and v2raygrpclite services.
This commit is contained in:
世界
2026-03-13 04:52:31 +08:00
parent 6829f91a06
commit b96ab4fef9
3 changed files with 6 additions and 3 deletions

View File

@@ -29,6 +29,7 @@ import (
"github.com/anthropics/anthropic-sdk-go"
"github.com/go-chi/chi/v5"
"golang.org/x/net/http2"
"golang.org/x/net/http2/h2c"
)
const (
@@ -249,7 +250,7 @@ func (s *Service) Start(stage adapter.StartStage) error {
router := chi.NewRouter()
router.Mount("/", s)
s.httpServer = &http.Server{Handler: router}
s.httpServer = &http.Server{Handler: h2c.NewHandler(router, &http2.Server{})}
if s.tlsConfig != nil {
err := s.tlsConfig.Start()

View File

@@ -30,6 +30,7 @@ import (
"github.com/openai/openai-go/v3"
"github.com/openai/openai-go/v3/responses"
"golang.org/x/net/http2"
"golang.org/x/net/http2/h2c"
)
func RegisterService(registry *boxService.Registry) {
@@ -302,7 +303,7 @@ func (s *Service) Start(stage adapter.StartStage) error {
router := chi.NewRouter()
router.Mount("/", s)
s.httpServer = &http.Server{Handler: router}
s.httpServer = &http.Server{Handler: h2c.NewHandler(router, &http2.Server{})}
if s.tlsConfig != nil {
err := s.tlsConfig.Start()

View File

@@ -22,6 +22,7 @@ import (
"github.com/go-chi/chi/v5"
"golang.org/x/net/http2"
"golang.org/x/net/http2/h2c"
)
func RegisterService(registry *boxService.Registry) {
@@ -59,7 +60,7 @@ func NewService(ctx context.Context, logger log.ContextLogger, tag string, optio
Listen: options.ListenOptions,
}),
httpServer: &http.Server{
Handler: chiRouter,
Handler: h2c.NewHandler(chiRouter, &http2.Server{}),
},
traffics: make(map[string]*TrafficManager),
users: make(map[string]*UserManager),