Skip to content

Stop cloud backtests when the requested push fails - #718

Merged
quantconnect-kronos[bot] merged 1 commit into
masterfrom
kronos/bug-717-stop-on-failed-push
Nov 13, 2026
Merged

quantconnect-kronos[bot] merged 1 commit into
masterfrom
kronos/bug-717-stop-on-failed-push

Conversation

@quantconnect-kronos

Copy link
Copy Markdown
Contributor

Closes #717

What changed and why

With --push, lean cloud backtest, lean cloud optimize and lean cloud live deploy push the local project first. When that push failed (for example a write-permission error or files over the size limit), PushManager.push_projects only logged a warning, and CloudProjectManager.get_cloud_project returned the existing cloud project because it already had a cloud ID. The command then compiled and ran the previous cloud files and exited 0.

  • PushManager.push_projects now returns True when every project and library was pushed and False otherwise. It still logs the same warnings and keeps pushing the remaining projects, so lean cloud push behaves as before.
  • CloudProjectManager.get_cloud_project(..., push=True) raises a new PushFailedError when the push fails, on both paths: project given by local name and project given by cloud name/id with a local copy. The command stops before compiling and exits 1 with:
    Error: Cannot push '<project>' to the cloud, aborting so the cloud does not run outdated files
  • PushFailedError is its own type (not RuntimeError) because lean cloud backtest rewrites any RuntimeError from get_cloud_project into a "No project ... found" message, which would hide the real cause.

Commands that call get_cloud_project with push=False are unchanged.

Tests

New tests:

  • test_push_manager.py: push_projects returns True on success and False when a project that already has a cloud ID fails to upload.
  • test_cloud_project_manager.py: get_cloud_project raises PushFailedError and does not look up the cloud project when the push fails, for a local project name and for a cloud id.
  • test_backtest.py: lean cloud backtest "Python Project" --push with an existing cloud ID and a failed upload (write-permission error) exits nonzero and never compiles or runs a backtest.

The new tests except the False return test fail without the fix.

  • python -m pytest -s -rs (Python 3.11): 2807 passed, 81 skipped
  • python static_analysis.py: BUILD PASSED
  • scripts/readme.py: README unchanged

Tested end to end against a cloud API, with a project that already had a cloud ID and a local file too large to upload (the update request returns 413):

  • CLI 1.0.233: printed Cannot push ... status code 413, then Started compiling, ran the backtest on the old files, exit 0.
  • This branch: printed the same push warning, then Error: Cannot push 'E2EPush717' to the cloud, aborting so the cloud does not run outdated files, no compile, exit 1.
  • This branch, after removing the large file: pushed, compiled and backtested as before, exit 0.

Question

lean cloud push itself still exits 0 when a project cannot be pushed (it only logs the warning), which I left as is because the issue is about the commands that run code afterwards. Should it also exit nonzero? That would be a separate change.

`lean cloud backtest --push`, `lean cloud optimize --push` and
`lean cloud live deploy --push` logged a push failure as a warning and then
ran the previous cloud files, exiting 0. PushManager.push_projects now
reports whether every project was pushed, and CloudProjectManager raises a
PushFailedError when a requested push fails, so the command exits nonzero
before compiling.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@quantconnect-kronos quantconnect-kronos Bot added kronos:develop:working develop: in progress kronos:review Request review labels Nov 13, 2026
@quantconnect-kronos-reviewer quantconnect-kronos-reviewer Bot added kronos:review:queued review: queued kronos:review:working review: in progress and removed kronos:review Request review kronos:review:queued review: queued labels Nov 13, 2026
@quantconnect-kronos-reviewer
quantconnect-kronos-reviewer Bot marked this pull request as ready for review November 13, 2026 20:22

@quantconnect-kronos-reviewer quantconnect-kronos-reviewer Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approving. This fixes #717 as the issue asks, and nothing outside it changed.

What I checked

  • Every caller of get_cloud_project: only cloud backtest, cloud optimize and cloud live deploy pass push=True. The others pass False and behave as before. lean cloud push ignores the new return value, so it behaves as before too.
  • Both push paths in get_cloud_project (by local name, and by cloud name/id with a local copy) now stop before projects.get and compile. PushFailedError isn't a RuntimeError, so cloud backtest no longer turns a failed push into "No project ... found". main.py prints it as Error: ... and exits 1.
  • Mocked push_projects in the existing tests returns a truthy Mock, so those tests are unaffected.
  • With the lean/components changes reverted, the 4 new tests fail and the 2 False-return checks still pass, which matches the description. With the fix, the full suite passes, except tests/ui/test_app.py::test_command_process_runs_the_cli_as_a_child_process. That test fails the same way without the fix, because my environment has an installed CLI version that differs from the dev one.
  • CI is green on every platform and Python version.
  • I also ran it end to end myself with a project that already had a cloud ID and a local file over the upload size limit. lean cloud backtest <name> --push and lean cloud backtest <cloud id> --push both printed the push warning, then Error: Cannot push ... aborting so the cloud does not run outdated files, didn't compile and exited 1. After I removed the file, the same command pushed and backtested as before, exit 0.

Your question about lean cloud push: making it exit nonzero changes a different command's behavior, which scripts may depend on. Leaving it out of this PR is right. Whether to change it is for a QuantConnect member to decide, in its own issue.

Other repositories: none need an update. The change is internal to the CLI, and the docs don't describe this exit status.

Risk: I set risk:low. The change is small and easy to revert. It only stops a run that would otherwise use stale cloud files after a push the user asked for already failed, so paths that work today are unchanged. The evidence covers it: tests that fail without the fix, green CI and an end-to-end run.

@quantconnect-kronos-reviewer quantconnect-kronos-reviewer Bot added risk:low Low risk and removed kronos:review:working review: in progress labels Nov 13, 2026
@quantconnect-kronos quantconnect-kronos Bot added the kronos:review Request review label Nov 13, 2026
@quantconnect-kronos-reviewer quantconnect-kronos-reviewer Bot added kronos:review:queued review: queued and removed kronos:review Request review labels Nov 13, 2026
@quantconnect-kronos-reviewer-2 quantconnect-kronos-reviewer-2 Bot added kronos:review:working review: in progress and removed kronos:review:queued review: queued labels Nov 13, 2026

@quantconnect-kronos-reviewer-2 quantconnect-kronos-reviewer-2 Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approved at caf182d. No blocking findings.

The change addresses #717 without changing successful pushes, push=False callers, or standalone lean cloud push. Both resolver paths stop after a failed requested upload. The dedicated exception also preserves the push-failure message instead of triggering backtest's project-not-found rewrite.

Verification

  • CI: 54 successful checks, 6 skipped.
  • Clean Python 3.11 environment, python -m pytest -q: 2807 passed, 81 skipped on the full rerun. The first run had one unrelated random-name collision (2806 passed, 81 skipped, 1 failed); tracked separately in #722, with a deterministic reproduction.
  • Affected push-manager, resolver, backtest, optimization and live-command tests: 154 passed, 3 skipped.
  • python static_analysis.py: BUILD PASSED, with five existing unused-import warnings.
  • Replacing the two changed component methods with their base-branch versions made four new tests fail, including the command exiting 0 after a rejected upload. The failure-return assertion alone also accepts the old None, but the resolver and command tests detect the original bug.
  • Additional local probes verified mixed-success batches, associated-library failure, empty batches, and a successful retry after failure.
  • Tested end to end with an existing cloud ID and an upload rejected with HTTP 413: backtest by local name and cloud ID, optimization, and live deployment each exited 1 before compilation. No live deployment was started. After removing the oversized source file, push, compilation and backtesting succeeded with exit 0.

Separate existing issues

I reproduced these on both the base branch and this commit, so they do not block this fix:

  • #719: referenced libraries are not uploaded by cloud commands' --push path.
  • #720: an ID-based --push skips a locally renamed project.
  • #721: a push-induced directory rename leaves the resolver reading the old configuration path.

No other repositories need an update for this change. Keeping standalone lean cloud push exit-status changes out of this PR preserves its scope.

Risk: risk:low retained. This is a small, reversible fix that stops execution after an upload the user requested has already failed. Successful paths remain unchanged, and regression tests, green CI and end-to-end checks support that behavior.

@quantconnect-kronos-reviewer-2 quantconnect-kronos-reviewer-2 Bot removed the kronos:review:working review: in progress label Nov 13, 2026
@quantconnect-kronos
quantconnect-kronos Bot merged commit f2606ef into master Nov 13, 2026
60 checks passed
@quantconnect-kronos
quantconnect-kronos Bot deleted the kronos/bug-717-stop-on-failed-push branch November 13, 2026 20:44
@quantconnect-kronos quantconnect-kronos Bot removed the kronos:develop:working develop: in progress label Nov 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

risk:low Low risk

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Stop cloud backtests when the requested push fails

0 participants