Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit f258232

Browse files
authored
chore: return json for disabled scim routes (coder#15222)
Customers reporting html pages returned to SCIM. Likely a disabled SCIM. We should just report a more consumable error by the SCIM provider. Previous behavior was a status code 200 HTML page
1 parent 81e99be commit f258232

File tree

2 files changed

+53
-0
lines changed

2 files changed

+53
-0
lines changed

enterprise/coderd/coderd.go

+12
Original file line numberDiff line numberDiff line change
@@ -465,6 +465,18 @@ func New(ctx context.Context, options *Options) (_ *API, err error) {
465465
r.Patch("/{id}", api.scimPatchUser)
466466
})
467467
})
468+
} else {
469+
// Show a helpful 404 error. Because this is not under the /api/v2 routes,
470+
// the frontend is the fallback. A html page is not a helpful error for
471+
// a SCIM provider. This JSON has a call to action that __may__ resolve
472+
// the issue.
473+
// Using Mount to cover all subroute possibilities.
474+
api.AGPL.RootHandler.Mount("/scim/v2", http.Handler(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
475+
httpapi.Write(r.Context(), w, http.StatusNotFound, codersdk.Response{
476+
Message: "SCIM is disabled, please contact your administrator if you believe this is an error",
477+
Detail: "SCIM endpoints are disabled if no SCIM is configured. Configure 'CODER_SCIM_AUTH_HEADER' to enable.",
478+
})
479+
})))
468480
}
469481

470482
meshTLSConfig, err := replicasync.CreateDERPMeshTLSConfig(options.AccessURL.Hostname(), options.TLSCertificates)

enterprise/coderd/coderd_test.go

+41
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ package coderd_test
33
import (
44
"bytes"
55
"context"
6+
"encoding/json"
67
"fmt"
78
"net/http"
89
"net/http/httptest"
@@ -503,6 +504,46 @@ func TestMultiReplica_EmptyRelayAddress_DisabledDERP(t *testing.T) {
503504
}
504505
}
505506

507+
func TestSCIMDisabled(t *testing.T) {
508+
t.Parallel()
509+
510+
cli, _ := coderdenttest.New(t, &coderdenttest.Options{})
511+
512+
checkPaths := []string{
513+
"/scim/v2",
514+
"/scim/v2/",
515+
"/scim/v2/users",
516+
"/scim/v2/Users",
517+
"/scim/v2/Users/",
518+
"/scim/v2/random/path/that/is/long",
519+
"/scim/v2/random/path/that/is/long.txt",
520+
}
521+
522+
for _, p := range checkPaths {
523+
p := p
524+
t.Run(p, func(t *testing.T) {
525+
t.Parallel()
526+
527+
u, err := cli.URL.Parse(p)
528+
require.NoError(t, err)
529+
530+
req, err := http.NewRequestWithContext(context.Background(), http.MethodGet, u.String(), nil)
531+
require.NoError(t, err)
532+
533+
resp, err := http.DefaultClient.Do(req)
534+
require.NoError(t, err)
535+
defer resp.Body.Close()
536+
require.Equal(t, http.StatusNotFound, resp.StatusCode)
537+
538+
var apiError codersdk.Response
539+
err = json.NewDecoder(resp.Body).Decode(&apiError)
540+
require.NoError(t, err)
541+
542+
require.Contains(t, apiError.Message, "SCIM is disabled")
543+
})
544+
}
545+
}
546+
506547
// testDBAuthzRole returns a context with a subject that has a role
507548
// with permissions required for test setup.
508549
func testDBAuthzRole(ctx context.Context) context.Context {

0 commit comments

Comments
 (0)