mirror of
https://github.com/NousResearch/hermes-agent.git
synced 2026-05-29 06:31:32 +00:00
feat(cli): wire --manual-paste into `hermes auth add and hermes model`
Register the new ``--manual-paste`` flag on both entry points and thread it through to the xAI loopback login: * ``hermes auth add xai-oauth --manual-paste`` — pool-add path, forwarded inside ``auth_commands.handle_auth_add``. * ``hermes model --manual-paste`` — model-picker path, forwarded by ``_model_flow_xai_oauth`` into the synthetic ``argparse.Namespace`` it passes to ``_login_xai_oauth``. The picker also now forwards ``--no-browser`` and ``--timeout`` for consistency (previously hardcoded to defaults regardless of CLI flags). Help text on both flags points at #26923 and names the browser-only remote consoles (Cloud Shell, Codespaces, EC2 Instance Connect) so users searching ``hermes --help`` can find the workaround.
This commit is contained in:
parent
5a5c265bcf
commit
cafbc9a734
2 changed files with 38 additions and 4 deletions
|
|
@ -339,6 +339,7 @@ def auth_add_command(args) -> None:
|
|||
creds = auth_mod._xai_oauth_loopback_login(
|
||||
timeout_seconds=getattr(args, "timeout", None) or 20.0,
|
||||
open_browser=not getattr(args, "no_browser", False),
|
||||
manual_paste=bool(getattr(args, "manual_paste", False)),
|
||||
)
|
||||
label = (getattr(args, "label", None) or "").strip() or label_from_token(
|
||||
creds["tokens"]["access_token"],
|
||||
|
|
|
|||
|
|
@ -2022,7 +2022,7 @@ def select_provider_and_model(args=None):
|
|||
elif selected_provider == "openai-codex":
|
||||
_model_flow_openai_codex(config, current_model)
|
||||
elif selected_provider == "xai-oauth":
|
||||
_model_flow_xai_oauth(config, current_model)
|
||||
_model_flow_xai_oauth(config, current_model, args=args)
|
||||
elif selected_provider == "qwen-oauth":
|
||||
_model_flow_qwen_oauth(config, current_model)
|
||||
elif selected_provider == "minimax-oauth":
|
||||
|
|
@ -2903,7 +2903,7 @@ def _model_flow_openai_codex(config, current_model=""):
|
|||
print("No change.")
|
||||
|
||||
|
||||
def _model_flow_xai_oauth(_config, current_model=""):
|
||||
def _model_flow_xai_oauth(_config, current_model="", *, args=None):
|
||||
"""xAI Grok OAuth (SuperGrok Subscription) provider: ensure logged in, then pick model."""
|
||||
from hermes_cli.auth import (
|
||||
get_xai_oauth_auth_status,
|
||||
|
|
@ -2934,7 +2934,15 @@ def _model_flow_xai_oauth(_config, current_model=""):
|
|||
print("Starting a fresh xAI OAuth login...")
|
||||
print()
|
||||
try:
|
||||
mock_args = argparse.Namespace()
|
||||
# Forward CLI flags from ``hermes model --manual-paste``
|
||||
# / ``--no-browser`` / ``--timeout`` into the loopback
|
||||
# login. Without this, browser-only remotes (#26923)
|
||||
# can't reach the manual-paste path via ``hermes model``.
|
||||
mock_args = argparse.Namespace(
|
||||
manual_paste=bool(getattr(args, "manual_paste", False)),
|
||||
no_browser=bool(getattr(args, "no_browser", False)),
|
||||
timeout=getattr(args, "timeout", None),
|
||||
)
|
||||
_login_xai_oauth(
|
||||
mock_args,
|
||||
PROVIDER_REGISTRY["xai-oauth"],
|
||||
|
|
@ -2952,7 +2960,11 @@ def _model_flow_xai_oauth(_config, current_model=""):
|
|||
print("Not logged into xAI Grok OAuth (SuperGrok Subscription). Starting login...")
|
||||
print()
|
||||
try:
|
||||
mock_args = argparse.Namespace()
|
||||
mock_args = argparse.Namespace(
|
||||
manual_paste=bool(getattr(args, "manual_paste", False)),
|
||||
no_browser=bool(getattr(args, "no_browser", False)),
|
||||
timeout=getattr(args, "timeout", None),
|
||||
)
|
||||
_login_xai_oauth(mock_args, PROVIDER_REGISTRY["xai-oauth"])
|
||||
except SystemExit:
|
||||
print("Login cancelled or failed.")
|
||||
|
|
@ -10041,6 +10053,16 @@ def main():
|
|||
action="store_true",
|
||||
help="Do not attempt to open the browser automatically during Nous login",
|
||||
)
|
||||
model_parser.add_argument(
|
||||
"--manual-paste",
|
||||
action="store_true",
|
||||
help=(
|
||||
"For loopback OAuth providers (xai-oauth, ...): skip the local "
|
||||
"callback listener and paste the failed callback URL from your "
|
||||
"browser instead. Use on browser-only remotes (Cloud Shell, "
|
||||
"Codespaces, EC2 Instance Connect, ...). See #26923."
|
||||
),
|
||||
)
|
||||
model_parser.add_argument(
|
||||
"--timeout",
|
||||
type=float,
|
||||
|
|
@ -10503,6 +10525,17 @@ def main():
|
|||
action="store_true",
|
||||
help="Do not auto-open a browser for OAuth login",
|
||||
)
|
||||
auth_add.add_argument(
|
||||
"--manual-paste",
|
||||
action="store_true",
|
||||
help=(
|
||||
"Skip the loopback callback listener and paste the failed "
|
||||
"callback URL from your browser instead. Use this on "
|
||||
"browser-only remotes (GCP Cloud Shell, GitHub Codespaces, "
|
||||
"EC2 Instance Connect, ...) where 127.0.0.1 on the remote "
|
||||
"isn't reachable from your laptop. See #26923."
|
||||
),
|
||||
)
|
||||
auth_add.add_argument(
|
||||
"--timeout", type=float, help="OAuth/network timeout in seconds"
|
||||
)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue