Code Farm: per-plot auto-replant pause and crop-lock check; community sync and node work
DevPlace CI / test (push) Failing after 44m45s
DevPlace CI / test (push) Failing after 44m45s
Continuous Delivery could never be turned off once a crop was planted. Add a one-shot per-plot "stop after harvest" flag (POST /game/plot/stop, Devii tool game_plot_stop, game_plots.stop_after_harvest), cleared by the next plant, autoreplant claim or Refactor. Autoreplant now also respects crop locks through the shared _crop_lock predicate. Plan and measurements in happyplanting.md. Also includes the pending community sync, node network and related work in the tree; the full suite passed (4999) with all of it. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,81 @@
|
||||
# retoor <retoor@molodetz.nl>
|
||||
|
||||
from datetime import datetime, timezone
|
||||
|
||||
from devplacepy.database import get_table
|
||||
from devplacepy.utils import generate_uid
|
||||
from tests.conftest import BASE_URL
|
||||
|
||||
|
||||
def make_community(slug):
|
||||
uid = generate_uid()
|
||||
get_table("communities").insert(
|
||||
{
|
||||
"uid": uid, "slug": slug, "name": slug, "query": slug, "url": f"https://{slug}.example.org", "origin": f"{slug}.example.org",
|
||||
"status": "ready", "enabled": 1, "interval_seconds": 86400, "run_count": 0, "failure_count": 0,
|
||||
"created_at": datetime.now(timezone.utc).isoformat(), "deleted_at": None, "deleted_by": None, "schema": "{}",
|
||||
}
|
||||
)
|
||||
return uid
|
||||
|
||||
|
||||
def make_run(community_uid, **extra):
|
||||
uid = generate_uid()
|
||||
get_table("community_runs").insert(
|
||||
{
|
||||
"uid": uid, "community_uid": community_uid, "started_at": datetime.now(timezone.utc).isoformat(), "finished_at": "",
|
||||
"status": "running", "dry_run": 0, "trigger": "admin", "collected": "", "pushed": "", "errors": "", "log": "first log line",
|
||||
**extra,
|
||||
}
|
||||
)
|
||||
return uid
|
||||
|
||||
|
||||
def test_the_run_page_updates_itself_and_stops_polling_when_the_run_ends(alice):
|
||||
page, _ = alice
|
||||
slug = f"live{generate_uid()[-8:]}"
|
||||
community = make_community(slug)
|
||||
run = make_run(community)
|
||||
page.goto(f"{BASE_URL}/admin/communities/{slug}/ledger?run={run}", wait_until="domcontentloaded")
|
||||
root = page.locator("[data-community-root]")
|
||||
root.wait_for(state="attached")
|
||||
assert root.get_attribute("data-busy") == "true"
|
||||
get_table("community_runs").update(
|
||||
{
|
||||
"uid": run, "status": "ok", "finished_at": datetime.now(timezone.utc).isoformat(), "verdict": "ok",
|
||||
"headline": "Everything synced and updated by itself.", "tally": '{"created": 2}', "log": "final log line",
|
||||
},
|
||||
["uid"],
|
||||
)
|
||||
page.locator("text=Everything synced and updated by itself.").wait_for(state="visible", timeout=15000)
|
||||
page.wait_for_function("document.querySelector('[data-community-root]').dataset.busy === 'false'", timeout=15000)
|
||||
assert "final log line" in page.locator("pre.community-log").text_content()
|
||||
|
||||
|
||||
def test_a_finished_run_page_does_not_poll(alice):
|
||||
page, _ = alice
|
||||
slug = f"idle{generate_uid()[-8:]}"
|
||||
community = make_community(slug)
|
||||
run = make_run(community, status="ok", finished_at=datetime.now(timezone.utc).isoformat(), verdict="ok", headline="Done.")
|
||||
requests = []
|
||||
page.on("request", lambda request: requests.append(request.url) if "/ledger" in request.url else None)
|
||||
page.goto(f"{BASE_URL}/admin/communities/{slug}/ledger?run={run}", wait_until="domcontentloaded")
|
||||
assert page.locator("[data-community-root]").get_attribute("data-busy") == "false"
|
||||
page.wait_for_timeout(4500)
|
||||
assert len(requests) == 1
|
||||
|
||||
|
||||
def test_the_community_page_follows_a_running_run(alice):
|
||||
page, _ = alice
|
||||
slug = f"page{generate_uid()[-8:]}"
|
||||
community = make_community(slug)
|
||||
run = make_run(community)
|
||||
page.goto(f"{BASE_URL}/admin/communities/{slug}", wait_until="domcontentloaded")
|
||||
banner = page.locator("text=A run or a discovery is in progress")
|
||||
banner.wait_for(state="visible")
|
||||
get_table("community_runs").update(
|
||||
{"uid": run, "status": "ok", "finished_at": datetime.now(timezone.utc).isoformat(), "verdict": "ok", "headline": "Finished while you watched."},
|
||||
["uid"],
|
||||
)
|
||||
page.locator("text=Finished while you watched.").wait_for(state="visible", timeout=15000)
|
||||
assert banner.count() == 0
|
||||
Reference in New Issue
Block a user