{"record":{"id":"7e07e8b0c7acee55","repo":"ory/hydra","slug":"errkeynotfound","errorCode":"errKeyNotFound","errorMessage":"key not found","messagePattern":"key not found","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"oryx/decoderx/http.go","lineNumber":82,"sourceCode":"\tParseErrorIgnoreConversionErrors parseErrorStrategy = iota + 1\n\n\t// ParseErrorUseEmptyValueOnConversionErrors will ignore any parse errors caused by strconv.Parse* and use the\n\t// default value of the type to be casted, e.g. float64(0), string(\"\").\n\t//\n\t// If the JSON Schema defines `{\"ratio\": {\"type\": \"number\"}}` but `ratio=foobar` then field\n\t// `ratio` will receive the default value for the primitive type (here `0.0` for `number`).\n\t// If the destination struct is a `json.RawMessage`, then the output will be `{\"ratio\": 0.0}`.\n\tParseErrorUseEmptyValueOnConversionErrors\n\n\t// ParseErrorReturnOnConversionErrors will abort and return with an error if strconv.Parse* returns\n\t// an error.\n\t//\n\t// If the JSON Schema defines `{\"ratio\": {\"type\": \"number\"}}` but `ratio=foobar` the parser aborts\n\t// and returns an error, here: `strconv.ParseFloat: parsing \"foobar\"`.\n\tParseErrorReturnOnConversionErrors\n)\n\nvar errKeyNotFound = errors.New(\"key not found\")\n\n// HTTPFormDecoder configures the HTTP decoder to only accept form-data\n// (application/x-www-form-urlencoded, multipart/form-data)\nfunc HTTPFormDecoder() HTTPDecoderOption {\n\treturn func(o *httpDecoderOptions) {\n\t\to.allowedContentTypes = []string{httpContentTypeMultipartForm, httpContentTypeURLEncodedForm}\n\t}\n}\n\n// HTTPJSONDecoder configures the HTTP decoder to only accept JSON data\n// (application/json).\nfunc HTTPJSONDecoder() HTTPDecoderOption {\n\treturn func(o *httpDecoderOptions) {\n\t\to.allowedContentTypes = []string{httpContentTypeJSON}\n\t}\n}\n\n// HTTPKeepRequestBody configures the HTTP decoder to allow other","sourceCodeStart":64,"sourceCodeEnd":100,"githubUrl":"https://github.com/ory/hydra/blob/4174065ffb052799890f7480f5360a877a67ffc1/oryx/decoderx/http.go#L64-L100","documentation":"decoderx's form decoder uses errKeyNotFound internally to signal that a required path/key was absent from the submitted form values. Callers like decodeURLValues' consumers check errors.Is(err, errKeyNotFound) to distinguish 'field missing' (often tolerated, e.g. partial PATCH forms) from genuine decode failures.","triggerScenarios":"Posting application/x-www-form-urlencoded or multipart/form-data data to an endpoint whose HTTPFormDecoder schema expects a field, when the field is absent from the request body; the decodeForm/decodeURLValues path then produces errKeyNotFound, which the caller at http.go:382 may swallow for optional-field handling.","commonSituations":"Partial form submissions (PATCH where only some fields are sent), clients omitting optional checkboxes, renamed form fields not matching the JSON schema keys, or tests posting empty bodies.","solutions":["Include the missing key in the submitted form data with a valid value.","If the field is optional in your API, tolerate errKeyNotFound via errors.Is(err, decoderx.ErrKeyNotFound-style check) as the library does, and proceed with a zero value.","Align the JSON schema field names with the actual form field names the client sends.","Verify Content-Type is form-urlencoded or multipart so the form decoder actually parses the values."],"exampleFix":"// before\nif err := d.Decode(r, &update); err != nil { return err }\n// after\nif err := d.Decode(r, &update); err != nil && !errors.Is(err, errKeyNotFound) {\n  return err\n}\n// missing keys then fall through to zero values","handlingStrategy":"type-guard","validationCode":"// on the client, before submitting:\nfor _, f := range requiredFields {\n  if r.Form.Get(f) == \"\" {\n    return fmt.Errorf(\"missing required form field %q\", f)\n  }\n}","typeGuard":"func isKeyNotFound(err error) bool { return errors.Is(err, errKeyNotFound) }","tryCatchPattern":"if err := decoder.Decode(r, &target); err != nil {\n  if errors.Is(err, errKeyNotFound) {\n    // optional field absent; proceed with zero value\n  } else {\n    return err\n  }\n}","preventionTips":["Match form field names exactly to the decoder's JSON schema keys","Model optional fields explicitly and tolerate key-not-found for them","Send a valid form Content-Type so values are parsed at all","Test PATCH-style partial submissions"],"tags":["http","forms","decoding","validation"],"backgroundTag":"missing-form-field","analyzedSha":"4174065ffb052799890f7480f5360a877a67ffc1","analyzedAt":"2026-09-03T14:52:41.581Z","contentChangedAt":"2026-09-03T14:52:41.581Z","schemaVersion":2},"datasetVersion":"2026-09-10T17:17:09.494Z"}