fix(s28): api-reference handle ~/path ASP.NET convention
Some checks failed
Auto-tag / Create date-tag (push) Waiting to run
CI / Backend (.NET 8) (push) Waiting to run
CI / Web (React + Vite) (push) Waiting to run
CI / POS (WPF, Windows) (push) Waiting to run
Docker API / Build + push API (push) Has been cancelled
Docker API / Deploy API on stage (push) Has been cancelled
Some checks failed
Auto-tag / Create date-tag (push) Waiting to run
CI / Backend (.NET 8) (push) Waiting to run
CI / Web (React + Vite) (push) Waiting to run
CI / POS (WPF, Windows) (push) Waiting to run
Docker API / Build + push API (push) Has been cancelled
Docker API / Deploy API on stage (push) Has been cancelled
ASP.NET Core convention для HttpX-атрибутов: `~/path` означает 'absolute from root, ignore class [Route]'. До фикса генератор клеил `base-route` + `~/path` → невалидный `/~/connect/token`. Теперь tilde корректно срезается, /connect/token виден в reference. Также добавлен unit test ApiReferenceDocsJobTests (Sprint 28) для lock-down regex behavior на double-nested generics. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
parent
5b87b5d599
commit
99b84132ba
|
|
@ -55,7 +55,7 @@ Base route: `/api/auth`
|
||||||
|
|
||||||
| Method | Route | Permission | Summary |
|
| Method | Route | Permission | Summary |
|
||||||
|---|---|---|---|
|
|---|---|---|---|
|
||||||
| POST | `/~/connect/token` | — | |
|
| POST | `/connect/token` | — | |
|
||||||
|
|
||||||
## `CounterpartiesController`
|
## `CounterpartiesController`
|
||||||
Base route: `/api/catalog/counterparties`
|
Base route: `/api/catalog/counterparties`
|
||||||
|
|
|
||||||
|
|
@ -125,8 +125,14 @@ def main() -> int:
|
||||||
if auth_m:
|
if auth_m:
|
||||||
perm = f'auth:{auth_m.group(1) or "any"}'
|
perm = f'auth:{auth_m.group(1) or "any"}'
|
||||||
# Compose full route.
|
# Compose full route.
|
||||||
parts = [p.strip('/') for p in (base, sub) if p]
|
# ASP.NET Core convention: `~/path` в HttpX-атрибуте означает
|
||||||
full = '/' + '/'.join(parts)
|
# "absolute from root, ignore class-level [Route]". Срезаем `~`
|
||||||
|
# и используем sub как абсолютный путь.
|
||||||
|
if sub.startswith('~/'):
|
||||||
|
full = sub[1:] # `~/connect/token` → `/connect/token`
|
||||||
|
else:
|
||||||
|
parts = [p.strip('/') for p in (base, sub) if p]
|
||||||
|
full = '/' + '/'.join(parts)
|
||||||
full = full.rstrip('/') or '/'
|
full = full.rstrip('/') or '/'
|
||||||
summary = find_doc_summary(txt, m.start())
|
summary = find_doc_summary(txt, m.start())
|
||||||
endpoints.append((cname, base, verb, full, perm, summary))
|
endpoints.append((cname, base, verb, full, perm, summary))
|
||||||
|
|
|
||||||
|
|
@ -132,7 +132,20 @@ private static IEnumerable<EndpointInfo> ScanDir(string dir)
|
||||||
if (!http.Success) continue;
|
if (!http.Success) continue;
|
||||||
var httpMethod = http.Groups[1].Value.ToUpperInvariant();
|
var httpMethod = http.Groups[1].Value.ToUpperInvariant();
|
||||||
var subRoute = http.Groups[2].Success ? http.Groups[2].Value : "";
|
var subRoute = http.Groups[2].Success ? http.Groups[2].Value : "";
|
||||||
var fullRoute = "/" + string.Join("/", new[] { baseRoute, subRoute }.Where(s => !string.IsNullOrEmpty(s))).Trim('/');
|
// Sprint 28: ASP.NET Core convention `~/path` означает "absolute
|
||||||
|
// from root, ignore class [Route]". Без обработки `~` попадал
|
||||||
|
// в начало пути и получался невалидный `/~/connect/token`.
|
||||||
|
string fullRoute;
|
||||||
|
if (subRoute.StartsWith("~/", StringComparison.Ordinal))
|
||||||
|
{
|
||||||
|
fullRoute = subRoute[1..]; // `~/connect/token` → `/connect/token`
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
fullRoute = "/" + string.Join("/",
|
||||||
|
new[] { baseRoute, subRoute }
|
||||||
|
.Where(s => !string.IsNullOrEmpty(s))).Trim('/');
|
||||||
|
}
|
||||||
|
|
||||||
var permMatch = Regex.Match(attrs, @"\[RequiresPermission\(""([^""]+)""\)\]");
|
var permMatch = Regex.Match(attrs, @"\[RequiresPermission\(""([^""]+)""\)\]");
|
||||||
var perm = permMatch.Success ? permMatch.Groups[1].Value : "";
|
var perm = permMatch.Success ? permMatch.Groups[1].Value : "";
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue