Fix OCI route mounting — integrate into authenticated /v2 group
NewRouter now accepts an optional OCI handler to mount inside the authenticated /v2 route group, avoiding chi's Mount conflict on an existing path. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -123,9 +123,7 @@ func runServer(configPath string) error {
|
|||||||
// Create OCI handler and HTTP router.
|
// Create OCI handler and HTTP router.
|
||||||
ociHandler := oci.NewHandler(database, store, policyEngine, auditFn)
|
ociHandler := oci.NewHandler(database, store, policyEngine, auditFn)
|
||||||
|
|
||||||
router := server.NewRouter(authClient, authClient, cfg.MCIAS.ServiceName)
|
router := server.NewRouter(authClient, authClient, cfg.MCIAS.ServiceName, ociHandler.Router())
|
||||||
// Mount OCI endpoints at /v2.
|
|
||||||
router.Mount("/v2", ociHandler.Router())
|
|
||||||
// Mount admin REST endpoints.
|
// Mount admin REST endpoints.
|
||||||
gcState := &server.GCState{
|
gcState := &server.GCState{
|
||||||
Collector: collector,
|
Collector: collector,
|
||||||
|
|||||||
@@ -1,10 +1,15 @@
|
|||||||
package server
|
package server
|
||||||
|
|
||||||
import "github.com/go-chi/chi/v5"
|
import (
|
||||||
|
"net/http"
|
||||||
|
|
||||||
|
"github.com/go-chi/chi/v5"
|
||||||
|
)
|
||||||
|
|
||||||
// NewRouter builds the chi router with all OCI Distribution Spec
|
// NewRouter builds the chi router with all OCI Distribution Spec
|
||||||
// endpoints and auth middleware wired up.
|
// endpoints and auth middleware wired up. If ociRouter is non-nil,
|
||||||
func NewRouter(validator TokenValidator, loginClient LoginClient, serviceName string) *chi.Mux {
|
// its routes are mounted under /v2 behind the auth middleware.
|
||||||
|
func NewRouter(validator TokenValidator, loginClient LoginClient, serviceName string, ociRouter http.Handler) *chi.Mux {
|
||||||
r := chi.NewRouter()
|
r := chi.NewRouter()
|
||||||
|
|
||||||
// Token endpoint is NOT behind RequireAuth — clients use Basic auth
|
// Token endpoint is NOT behind RequireAuth — clients use Basic auth
|
||||||
@@ -15,6 +20,9 @@ func NewRouter(validator TokenValidator, loginClient LoginClient, serviceName st
|
|||||||
r.Route("/v2", func(v2 chi.Router) {
|
r.Route("/v2", func(v2 chi.Router) {
|
||||||
v2.Use(RequireAuth(validator, serviceName))
|
v2.Use(RequireAuth(validator, serviceName))
|
||||||
v2.Get("/", V2Handler())
|
v2.Get("/", V2Handler())
|
||||||
|
if ociRouter != nil {
|
||||||
|
v2.Mount("/", ociRouter)
|
||||||
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
return r
|
return r
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ func TestRoutesV2Authenticated(t *testing.T) {
|
|||||||
claims: &auth.Claims{Subject: "alice", AccountType: "user", Roles: []string{"reader"}},
|
claims: &auth.Claims{Subject: "alice", AccountType: "user", Roles: []string{"reader"}},
|
||||||
}
|
}
|
||||||
loginClient := &fakeLoginClient{token: "tok-abc", expiresIn: 3600}
|
loginClient := &fakeLoginClient{token: "tok-abc", expiresIn: 3600}
|
||||||
router := NewRouter(validator, loginClient, "mcr-test")
|
router := NewRouter(validator, loginClient, "mcr-test", nil)
|
||||||
|
|
||||||
req := httptest.NewRequest(http.MethodGet, "/v2/", nil)
|
req := httptest.NewRequest(http.MethodGet, "/v2/", nil)
|
||||||
req.Header.Set("Authorization", "Bearer valid-token")
|
req.Header.Set("Authorization", "Bearer valid-token")
|
||||||
@@ -42,7 +42,7 @@ func TestRoutesV2Unauthenticated(t *testing.T) {
|
|||||||
t.Helper()
|
t.Helper()
|
||||||
validator := &fakeValidator{claims: nil, err: auth.ErrUnauthorized}
|
validator := &fakeValidator{claims: nil, err: auth.ErrUnauthorized}
|
||||||
loginClient := &fakeLoginClient{}
|
loginClient := &fakeLoginClient{}
|
||||||
router := NewRouter(validator, loginClient, "mcr-test")
|
router := NewRouter(validator, loginClient, "mcr-test", nil)
|
||||||
|
|
||||||
req := httptest.NewRequest(http.MethodGet, "/v2/", nil)
|
req := httptest.NewRequest(http.MethodGet, "/v2/", nil)
|
||||||
// No Authorization header.
|
// No Authorization header.
|
||||||
@@ -66,7 +66,7 @@ func TestRoutesTokenEndpoint(t *testing.T) {
|
|||||||
// The validator should never be called for /v2/token.
|
// The validator should never be called for /v2/token.
|
||||||
validator := &fakeValidator{claims: nil, err: auth.ErrUnauthorized}
|
validator := &fakeValidator{claims: nil, err: auth.ErrUnauthorized}
|
||||||
loginClient := &fakeLoginClient{token: "tok-from-login", expiresIn: 1800}
|
loginClient := &fakeLoginClient{token: "tok-from-login", expiresIn: 1800}
|
||||||
router := NewRouter(validator, loginClient, "mcr-test")
|
router := NewRouter(validator, loginClient, "mcr-test", nil)
|
||||||
|
|
||||||
req := httptest.NewRequest(http.MethodGet, "/v2/token", nil)
|
req := httptest.NewRequest(http.MethodGet, "/v2/token", nil)
|
||||||
req.SetBasicAuth("bob", "password")
|
req.SetBasicAuth("bob", "password")
|
||||||
|
|||||||
Reference in New Issue
Block a user