reactiveui/refit · error · ArgumentException
URL {relativePathTemplate} has parameter {{{key}}}, but no m
Error message
URL {relativePathTemplate} has parameter {{{key}}}, but no method parameter matches What it means
Thrown when a route template contains a {key} placeholder that no method parameter supplies. After locating a '{' and its matching '}', the builder extracts the key and throws an ArgumentException naming the unmatched placeholder and the template. It is a design-time contract violation surfaced at request build time.
Source
Thrown at src/Refit/GeneratedRequestRunner.cs:697
if (allowUnmatchedParameter)
{
return path;
}
var i = path.IndexOf('{');
if (i < 0)
{
return path;
}
var j = path.AsSpan(i).IndexOfAny('}', '/');
if (j < 0 || path[j += i] != '}')
{
return path;
}
var key = path[(i + 1)..j];
throw new ArgumentException(
$"URL {relativePathTemplate} has parameter {{{key}}}, but no method parameter matches");
}
/// <summary>Rejects a no-leading-slash path under legacy resolution, matching the reflection request builder.</summary>
/// <param name="relativePath">The resolved relative request path.</param>
/// <exception cref="ArgumentException">The path is non-empty and does not start with '/'.</exception>
internal static void RequireLeadingSlashUnderLegacy(string relativePath)
{
if (relativePath.Length == 0 || relativePath[0] == '/')
{
return;
}
throw new ArgumentException(
$"URL path {relativePath} must start with '/' and be of the form '/foo/bar/baz'");
}
/// <summary>Builds the message describing an invalid <c>[Url]</c> parameter value.</summary>View on GitHub (pinned to b455f65ecc)
Solutions
- Add a method parameter whose name matches the {key} in the route template exactly
- Fix the typo so the template placeholder and parameter name agree (C# identifiers are case-sensitive)
- Remove the unused {key} from the route template if it is no longer needed
- If unmatched placeholders are intentional, set allowUnmatchedParameter so the builder skips them instead of throwing
Example fix
// before
[Get("/items/{id}/children/{childId}")]
Task<IList<Child>> GetChildrenAsync(long id);
// childId has no parameter => throws
// after
[Get("/items/{id}/children/{childId}")]
Task<IList<Child>> GetChildrenAsync(long id, long childId); Defensive patterns
Strategy: validation
Validate before calling
// Design-time: ensure every {key} in a route template has a matching parameter.
static IEnumerable<string> UnmatchedPlaceholders(string template, IEnumerable<string> paramNames)
{
var nameSet = paramNames.ToHashSet();
var matches = System.Text.RegularExpressions.Regex.Matches(template, @"\{(\w+)\}");
foreach (System.Text.RegularExpressions.Match m in matches)
if (!nameSet.Contains(m.Groups[1].Value))
yield return m.Groups[1].Value;
} Try / catch
try { await api.GetChildrenAsync(id, childId); }
catch (ArgumentException ex) when (ex.Message.Contains("but no method parameter matches"))
{
// interface/template mismatch - fix the route or add the parameter
} Prevention
- Treat every {key} in a route template as requiring an identically named parameter
- Add a build-time test that scans all interface routes for unmatched placeholders
- Rename parameters and template placeholders together to keep them in sync
- Use allowUnmatchedParameter only when unmatched placeholders are intentional
When it happens
Trigger: An interface method declares a route like [Get("/items/{id}/sub/{subId}")] but only has an 'id' parameter (subId missing), or a placeholder name has a typo differing from the parameter name. Each template token must correspond to a parameter passed via the uriParams collection.
Common situations: Refactoring a route and forgetting to add/remove the matching parameter; copy-paste typos between the template placeholder and the parameter name; renaming a parameter without updating the template; relying on a parameter that was conditionally compiled out.
Related errors
- URL path {relativePath} must start with '/' and be of the fo
- The [Url] parameter value "{value}" must be an absolute URI
- URL {relativePath} has parameter {rawName}, but no method pa
- Parameter {owner.Name} matches both a parameter and nested p
- A [Url] method must not also declare a path template; [Url]
AI-assisted analysis of reactiveui/refit@b455f65ecc (2026-08-13).
Data as JSON: /api/errors/56f9f8ef8c773737.
Report an issue: GitHub.