ci / gitleaks (push) Successful in 8s
ci / docs-check (push) Failing after 30s
ci / lint (push) Successful in 42s
ci / test-integration (push) Successful in 46s
ci / security (push) Failing after 27s
ci / test-mcp (push) Successful in 1m16s
ci / test-unit (push) Successful in 2m17s
ci / build-and-push (push) Successful in 17s
Identity gains a redact field that the executor honours, so the OAuth resolver no longer needs an executor subclass overriding private internals. Opaque agm_ tokens issued by our authorization server are now masked by the secret patterns wherever they appear in content.
39 lines
1.4 KiB
Python
39 lines
1.4 KiB
Python
"""Identity a tool call runs as.
|
|
|
|
Admin-token mode uses the configured ``GITEA_TOKEN`` (stdio, or the static MCP
|
|
bearer on HTTP). OAuth mode uses the signed-in user's own Gitea token. The
|
|
identity travels with each call so the executor can pick the right token and the
|
|
result envelope and audit log can name who acted.
|
|
"""
|
|
|
|
from __future__ import annotations
|
|
|
|
from dataclasses import dataclass, field
|
|
from typing import Any, Literal
|
|
|
|
IdentityMode = Literal["admin-token", "oauth"]
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class Identity:
|
|
"""Who a tool call acts as.
|
|
|
|
Attributes:
|
|
login: Gitea login when known (``None`` until resolved).
|
|
mode: ``admin-token`` or ``oauth``.
|
|
token: Gitea token for this identity. Excluded from ``repr`` and never
|
|
part of :meth:`metadata`.
|
|
redact: Further secrets of this identity (for example the OAuth user's
|
|
Gitea refresh token) that the executor replaces in every result.
|
|
Excluded from ``repr`` and comparisons.
|
|
"""
|
|
|
|
login: str | None
|
|
mode: IdentityMode
|
|
token: str = field(repr=False)
|
|
redact: tuple[str, ...] = field(default=(), repr=False, compare=False)
|
|
|
|
def metadata(self, sudo: str | None = None) -> dict[str, Any]:
|
|
"""Return result and audit metadata: ``{"login", "mode", "sudo"}``, never the token."""
|
|
return {"login": self.login, "mode": self.mode, "sudo": sudo}
|