mainsequence 8.1.27.dev28__tar.gz → 8.1.27.dev29__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {mainsequence-8.1.27.dev28/mainsequence.egg-info → mainsequence-8.1.27.dev29}/PKG-INFO +1 -1
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/cli.py +8 -1
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29/mainsequence.egg-info}/PKG-INFO +1 -1
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/pyproject.toml +1 -1
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_cli_auth_contract.py +26 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/LICENSE +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/README.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/AGENTS.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/a2a_sdk_execution/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/application_surfaces/api_surfaces/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/maintenance/bug_auditor/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/maintenance/code_repository_maintenance/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/maintenance/metatables_transition/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/platform_operations/access_control_and_sharing/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/platform_operations/orchestration_and_releases/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/agent_scaffold/skills/sdk_code_repository_execution/SKILL.md +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/__init__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/__main__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/_request_identity.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/bootstrap.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/__init__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/api.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/browser_auth.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/code_repository_status.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/config.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/docker_utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/doctor.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/local_ops.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/model_filters.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/pydantic_cli.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/sdk_utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/ssh_utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/ui.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/__init__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/agent_runtime_models.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/base.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/client.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/compute_validation.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/exceptions.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/github_issues.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/models_foundry.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/models_helpers.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/models_user.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/observability.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/value_sets.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/code_repository_context.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/code_repository_skills.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/defaults.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/instrumentation/__init__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/instrumentation/utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/logconf.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/repository_identity_security.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/runtime_flags.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/scaffold_skills.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/server/__init__.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/server/caller_assertions.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/server/fastapi.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/SOURCES.txt +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/dependency_links.txt +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/entry_points.txt +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/requires.txt +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/top_level.txt +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/setup.cfg +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_auth_bootstrap.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_auth_precedence.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_caller_assertions.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_canonical_api_route_contract.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_cli.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_cli_browser_auth.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_cli_secure_storage.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_client.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_code_repository_branch_contract.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_code_repository_documentation_contract.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_code_repository_runtime_context.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_code_repository_skills.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_dependency_extras.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_dev_release_version.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_environment_resource_context.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_environment_response_contracts.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_fastapi_request_identity.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_filter_normalization.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_github_issues_client.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_independent_context.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_instrumentation.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_job_client.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_local_ops.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_logconf.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_models_user_request_bound_auth.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_notification_uid_contract.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_observability_client.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_scaffold_skills.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_secret_client_model.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_source_ownership.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_ssh_utils.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_tolerant_response_reading.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_tolerant_value_sets.py +0 -0
- {mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_user_application_facts.py +0 -0
|
@@ -44,6 +44,7 @@ from textwrap import dedent
|
|
|
44
44
|
from typing import NoReturn
|
|
45
45
|
|
|
46
46
|
import click
|
|
47
|
+
import requests
|
|
47
48
|
import typer
|
|
48
49
|
from packaging.specifiers import InvalidSpecifier, SpecifierSet
|
|
49
50
|
from packaging.version import InvalidVersion, Version
|
|
@@ -713,7 +714,8 @@ def _require_login() -> dict:
|
|
|
713
714
|
Returns:
|
|
714
715
|
profile dict
|
|
715
716
|
|
|
716
|
-
Raises typer.Exit(1) with user-friendly message on failure
|
|
717
|
+
Raises typer.Exit(1) with user-friendly message on failure: a missing or
|
|
718
|
+
rejected session, or a backend that could not be reached.
|
|
717
719
|
"""
|
|
718
720
|
try:
|
|
719
721
|
prof = get_current_user_profile()
|
|
@@ -726,6 +728,11 @@ def _require_login() -> dict:
|
|
|
726
728
|
except ApiError as e:
|
|
727
729
|
error("Not logged in. Run: mainsequence login")
|
|
728
730
|
raise typer.Exit(1) from e
|
|
731
|
+
except (requests.exceptions.ConnectionError, requests.exceptions.Timeout) as e:
|
|
732
|
+
# The backend gave no answer about the session, so this is not "Not logged in".
|
|
733
|
+
# Never echo the exception: a transport error can carry request details.
|
|
734
|
+
error(f"The backend at {cfg.backend_url()} could not be reached ({type(e).__name__}).")
|
|
735
|
+
raise typer.Exit(1) from e
|
|
729
736
|
|
|
730
737
|
|
|
731
738
|
def _runtime_credential_mode_enabled() -> bool:
|
|
@@ -5,6 +5,7 @@ from __future__ import annotations
|
|
|
5
5
|
import json
|
|
6
6
|
|
|
7
7
|
import pytest
|
|
8
|
+
import requests
|
|
8
9
|
from typer.testing import CliRunner
|
|
9
10
|
|
|
10
11
|
from mainsequence.cli import cli as cli_mod
|
|
@@ -364,6 +365,31 @@ def test_auth_status_check_asks_the_backend(monkeypatch):
|
|
|
364
365
|
assert json.loads(refused.output)["authenticated"] is False
|
|
365
366
|
|
|
366
367
|
|
|
368
|
+
@pytest.mark.parametrize(
|
|
369
|
+
"failure", [requests.exceptions.ConnectionError, requests.exceptions.ReadTimeout]
|
|
370
|
+
)
|
|
371
|
+
def test_login_check_says_when_the_backend_could_not_be_reached(monkeypatch, failure):
|
|
372
|
+
def unreachable():
|
|
373
|
+
raise failure(
|
|
374
|
+
"HTTPSConnectionPool(host='backend.example', port=443): Max retries exceeded "
|
|
375
|
+
"with url: /api/v1/users/me/"
|
|
376
|
+
)
|
|
377
|
+
|
|
378
|
+
monkeypatch.setattr(cli_mod.cfg, "backend_url", lambda: "https://backend.example")
|
|
379
|
+
monkeypatch.setattr(cli_mod, "get_current_user_profile", unreachable)
|
|
380
|
+
|
|
381
|
+
result = runner.invoke(cli_mod.app, ["code-repository", "list"])
|
|
382
|
+
|
|
383
|
+
assert result.exit_code == 1
|
|
384
|
+
# The command ended itself; an exception that escapes it is what prints a traceback.
|
|
385
|
+
assert isinstance(result.exception, SystemExit)
|
|
386
|
+
assert "Traceback" not in result.output
|
|
387
|
+
# One line, and no "Not logged in": the backend never judged the session.
|
|
388
|
+
assert result.output == (
|
|
389
|
+
f"The backend at https://backend.example could not be reached ({failure.__name__}).\n"
|
|
390
|
+
)
|
|
391
|
+
|
|
392
|
+
|
|
367
393
|
def _now() -> int:
|
|
368
394
|
import time
|
|
369
395
|
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/cli/code_repository_status.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/agent_runtime_models.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/compute_validation.py
RENAMED
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/github_issues.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/models_foundry.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/models_helpers.py
RENAMED
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/client/observability.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/code_repository_context.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/code_repository_skills.py
RENAMED
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/instrumentation/__init__.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/instrumentation/utils.py
RENAMED
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/repository_identity_security.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence/server/caller_assertions.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/mainsequence.egg-info/entry_points.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_canonical_api_route_contract.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_code_repository_skills.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_environment_resource_context.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_environment_response_contracts.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_fastapi_request_identity.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_models_user_request_bound_auth.py
RENAMED
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_notification_uid_contract.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_tolerant_response_reading.py
RENAMED
|
File without changes
|
|
File without changes
|
{mainsequence-8.1.27.dev28 → mainsequence-8.1.27.dev29}/tests/test_user_application_facts.py
RENAMED
|
File without changes
|