{"record":{"id":"851db237529080f2","repo":"caddyserver/caddy","slug":"request-path-is-missing-object-id","errorCode":null,"errorMessage":"request path is missing object ID","messagePattern":"request path is missing object ID","errorType":"http","errorClass":"APIError","httpStatus":400,"severity":"error","filePath":"admin.go","lineNumber":1098,"sourceCode":"\n\tdefault:\n\t\treturn APIError{\n\t\t\tHTTPStatus: http.StatusMethodNotAllowed,\n\t\t\tErr:        fmt.Errorf(\"method %s not allowed\", r.Method),\n\t\t}\n\t}\n\n\treturn nil\n}\n\nfunc handleConfigID(w http.ResponseWriter, r *http.Request) error {\n\tidPath := r.URL.Path\n\n\tparts := strings.Split(idPath, \"/\")\n\tif len(parts) < 3 || parts[2] == \"\" {\n\t\treturn APIError{\n\t\t\tHTTPStatus: http.StatusBadRequest,\n\t\t\tErr:        fmt.Errorf(\"request path is missing object ID\"),\n\t\t}\n\t}\n\tif parts[0] != \"\" || parts[1] != \"id\" {\n\t\treturn APIError{\n\t\t\tHTTPStatus: http.StatusBadRequest,\n\t\t\tErr:        fmt.Errorf(\"malformed object path\"),\n\t\t}\n\t}\n\tid := parts[2]\n\n\t// map the ID to the expanded path\n\trawCfgMu.RLock()\n\texpanded, ok := rawCfgIndex[id]\n\trawCfgMu.RUnlock()\n\tif !ok {\n\t\treturn APIError{\n\t\t\tHTTPStatus: http.StatusNotFound,\n\t\t\tErr:        fmt.Errorf(\"unknown object ID '%s'\", id),","sourceCodeStart":1080,"sourceCodeEnd":1116,"githubUrl":"https://github.com/caddyserver/caddy/blob/50e54ee279aa1e504fe218ca49ab6ae16c100410/admin.go#L1080-L1116","documentation":"Thrown by Caddy's admin API handleConfigID handler when a request to the /id/ endpoint has a path with no object ID after the prefix. The handler splits r.URL.Path on '/' and requires at least three parts with a non-empty third segment. It returns HTTP 400 with the message 'request path is missing object ID'.","triggerScenarios":"Any HTTP request to the admin endpoint whose path is exactly '/id/' or '/id' (e.g. curl http://localhost:2019/id/ or GET /id). Requests that use the ID-based config path form but forget to append the @id value.","commonSituations":"Scripts or tooling that build the /id/<ID> URL dynamically and pass an empty ID variable; copy-paste from docs that omit the placeholder; clients that URL-trim the trailing ID.","solutions":["Append the actual object ID (its @id field from the config) after /id/, e.g. GET http://localhost:2019/id/my-route","First GET /config/ or the raw config JSON to find the @id value you meant to reference","If you do not need ID-based addressing, use the canonical /config/... path instead"],"exampleFix":"# before\ncurl http://localhost:2019/id/\n# after\ncurl http://localhost:2019/id/httpserver/routes/0","handlingStrategy":"validation","validationCode":"# Validate the URL has a non-empty ID before calling\nreq_url=\"http://localhost:2019/id/${OBJ_ID:?OBJ_ID must be set}\"\ncurl -f \"$req_url\"","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Fail fast in scripts: use shell ${VAR:?} so an empty ID aborts before the request","Fetch @id values from the live config instead of hardcoding them"],"tags":["caddy","admin-api","http","routing","bad-request"],"backgroundTag":null,"analyzedSha":"50e54ee279aa1e504fe218ca49ab6ae16c100410","analyzedAt":"2026-08-15T09:20:21.641Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}