diff --git a/http/events.go b/http/events.go index aba3bb45cec8..478f31704250 100644 --- a/http/events.go +++ b/http/events.go @@ -81,8 +81,8 @@ func handleEventsSubscribe(core *vault.Core) http.Handler { } prefix := "/v1/sys/events/subscribe/" - if ns.ID != "root" { - prefix = fmt.Sprintf("/v1/%s/sys/events/subscribe/", ns.Path) + if ns.ID != namespace.RootNamespaceID { + prefix = fmt.Sprintf("/v1/%ssys/events/subscribe/", ns.Path) } eventTypeStr := strings.TrimSpace(strings.TrimPrefix(r.URL.Path, prefix)) if eventTypeStr == "" { diff --git a/http/handler.go b/http/handler.go index 601aa803779a..34c4b12cf19c 100644 --- a/http/handler.go +++ b/http/handler.go @@ -26,7 +26,6 @@ import ( "github.com/hashicorp/go-secure-stdlib/parseutil" "github.com/hashicorp/go-sockaddr" "github.com/hashicorp/go-uuid" - "github.com/hashicorp/vault/helper/experiments" "github.com/hashicorp/vault/helper/namespace" "github.com/hashicorp/vault/internalshared/configutil" "github.com/hashicorp/vault/sdk/helper/consts" @@ -177,10 +176,6 @@ func handler(props *vault.HandlerProperties) http.Handler { mux.Handle("/v1/sys/storage/raft/join", handleSysRaftJoin(core)) mux.Handle("/v1/sys/internal/ui/feature-flags", handleSysInternalFeatureFlags(core)) - if core.IsExperimentEnabled(experiments.VaultExperimentEventsAlpha1) { - mux.Handle("/v1/sys/events/subscribe/", handleEventsSubscribe(core)) - } - for _, path := range injectDataIntoTopRoutes { mux.Handle(path, handleRequestForwarding(core, handleLogicalWithInjector(core))) } diff --git a/http/logical.go b/http/logical.go index 6cdf6bb07110..7dc3ad9e832e 100644 --- a/http/logical.go +++ b/http/logical.go @@ -14,6 +14,7 @@ import ( "time" uuid "github.com/hashicorp/go-uuid" + "github.com/hashicorp/vault/helper/experiments" "github.com/hashicorp/vault/helper/namespace" "github.com/hashicorp/vault/sdk/helper/consts" "github.com/hashicorp/vault/sdk/logical" @@ -346,6 +347,24 @@ func handleLogicalInternal(core *vault.Core, injectDataIntoTopLevel bool, noForw return } + // Websockets need to be handled at HTTP layer instead of logical requests. + if core.IsExperimentEnabled(experiments.VaultExperimentEventsAlpha1) { + ns, err := namespace.FromContext(r.Context()) + if err != nil { + respondError(w, http.StatusInternalServerError, err) + return + } + nsPath := ns.Path + if ns.ID == namespace.RootNamespaceID { + nsPath = "" + } + if strings.HasPrefix(r.URL.Path, fmt.Sprintf("/v1/%ssys/events/subscribe/", nsPath)) { + handler := handleEventsSubscribe(core) + handler.ServeHTTP(w, r) + return + } + } + // Make the internal request. We attach the connection info // as well in case this is an authentication request that requires // it. Vault core handles stripping this if we need to. This also