{"record":{"id":"afb683277efdda1d","repo":"reactiveui/refit","slug":"method-must-be-defined-and-have-an-http-method-att","errorCode":null,"errorMessage":"Method must be defined and have an HTTP Method attribute","messagePattern":"Method must be defined and have an HTTP Method attribute","errorType":"validation","errorClass":"ArgumentException","httpStatus":null,"severity":"error","filePath":"src/Refit.Reflection/RequestBuilderImplementation.cs","lineNumber":374,"sourceCode":"\n    /// <summary>Finds the rest method matching the given name, parameter types and generic arguments.</summary>\n    /// <param name=\"key\">The method lookup key.</param>\n    /// <param name=\"parameterTypes\">The parameter types to match, or null to match a single overload.</param>\n    /// <param name=\"genericArgumentTypes\">The generic argument types to close over, or null.</param>\n    /// <returns>The matching rest method info.</returns>\n    /// <exception cref=\"ArgumentException\">No method matching <paramref name=\"key\"/> carries an HTTP method attribute,\n    /// or the name is overloaded and <paramref name=\"parameterTypes\"/> was not supplied to disambiguate it.</exception>\n    /// <exception cref=\"InvalidOperationException\">None of the overloads accept <paramref name=\"parameterTypes\"/> once closed over <paramref name=\"genericArgumentTypes\"/>.</exception>\n    [RequiresUnreferencedCode(\"Resolving generic Refit methods from reflected metadata requires generic method metadata to be available at runtime.\")]\n    [RequiresDynamicCode(\"Resolving generic Refit methods from reflected metadata requires runtime generic method instantiation.\")]\n    internal RestMethodInfoInternal FindMatchingRestMethodInfo(\n        string key,\n        Type[]? parameterTypes,\n        Type[]? genericArgumentTypes)\n    {\n        if (!_interfaceHttpMethods.TryGetValue(key, out var httpMethods))\n        {\n            throw new ArgumentException(\n                \"Method must be defined and have an HTTP Method attribute\");\n        }\n\n        if (parameterTypes is null)\n        {\n            if (httpMethods.Count > 1)\n            {\n                throw new ArgumentException(\n                    $\"MethodName exists more than once, '{nameof(parameterTypes)}' mut be defined\");\n            }\n\n            return CloseGenericMethodIfNeeded(httpMethods[0], genericArgumentTypes);\n        }\n\n        var possibleMethods = FilterPossibleMethods(httpMethods, parameterTypes, genericArgumentTypes);\n\n        if (possibleMethods.Length == 1)\n        {","sourceCodeStart":356,"sourceCodeEnd":392,"githubUrl":"https://github.com/reactiveui/refit/blob/b455f65ecc4c97d092317e349cb775f9cfc6bcdf/src/Refit.Reflection/RequestBuilderImplementation.cs#L356-L392","documentation":"FindMatchingRestMethodInfo looks up a method name key in the dictionary of HTTP-attributed methods. The dictionary is populated only from interface methods carrying an HTTP method attribute (Get/Post/etc.), so a missing key means the name does not exist on the interface or was never given an HTTP attribute. This is raised during method resolution, typically at the first call to that member.","triggerScenarios":"Invoking/reflecting a Refit method by a name not present in _interfaceHttpMethods, e.g. a method declared without [Get]/[Post]/... or a typo in a dynamic/keyed call, or calling a method that exists but is not a Refit HTTP method.","commonSituations":"Forgot the HTTP attribute on an interface method; renamed the method but the caller uses the old name; an inherited non-HTTP helper method is invoked through the proxy; mixed a Refit interface with plain helper methods.","solutions":["Add an HTTP method attribute ([Get]/[Post]/[Put]/[Patch]/[Delete]/[Head]) to the target interface method.","Verify the method name you are calling exactly matches the interface member name.","Remove non-HTTP helper methods from the Refit interface, or move them to a separate service."],"exampleFix":"// before\npublic interface IApi {\n    Task<User> GetUserAsync(string id); // no attribute -> not registered\n}\n\n// after\npublic interface IApi {\n    [Get(\"/users/{id}\")] Task<User> GetUserAsync(string id);\n}","handlingStrategy":"validation","validationCode":"// Validate at startup that every interface method has an HTTP attribute.\nstatic void AssertAllMethodsAttributed<T>() {\n    foreach (var m in typeof(T).GetMethods())\n        if (m.GetCustomAttribute<Refit.HttpMethodAttribute>() is null)\n            throw new InvalidOperationException($\"{typeof(T).Name}.{m.Name} has no HTTP method attribute.\");\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Decorate every interface method with an HTTP verb attribute.","Keep non-HTTP helpers off the Refit interface.","Run a startup reflection check over registered interfaces."],"tags":["refit","attributes","http-method","reflection","design-time"],"backgroundTag":null,"analyzedSha":"b455f65ecc4c97d092317e349cb775f9cfc6bcdf","analyzedAt":"2026-08-13T21:20:57.878Z","schemaVersion":2},"datasetVersion":"2026-08-14T00:17:13.853Z"}