Интегрирован wesp в сайт
CI / quality (push) Canceled after 0s

This commit is contained in:
влад
2026-07-17 12:57:18 +03:00
parent 5dfa06ddbe
commit 355c0ef9f1
883 changed files with 194576 additions and 177 deletions
@@ -0,0 +1,159 @@
"""E2E: два терминала — DnD/sync (баготест #4)."""
from __future__ import annotations
import pytest
from tests.e2e.recipes_e2e_helpers import (
drag_reorder_recipe,
list_dom_recipe_ids,
period_recipe_ids,
)
pytestmark = pytest.mark.e2e
SCENARIO_DUAL_E2E_DND_SYNC = "DUAL_E2E_DND_SYNC"
SCENARIO_DUAL_E2E_TRANSFER_REORDER = "DUAL_E2E_TRANSFER_REORDER"
def test_dual_reorder_visible_on_both_terminals(
page_a, page_b, dual_harness, live_server_a_url, live_server_b_url
) -> None:
SCENARIO_DUAL_E2E_DND_SYNC # noqa: F841
disp_id = dual_harness._e2e_disp_id # type: ignore[attr-defined]
period_a = dual_harness._e2e_period_a # type: ignore[attr-defined]
r1 = dual_harness._e2e_r1 # type: ignore[attr-defined]
r2 = dual_harness._e2e_r2 # type: ignore[attr-defined]
for page, url in ((page_a, live_server_a_url), (page_b, live_server_b_url)):
page.locator(f'[data-action="select-dispenser"][data-dispenser-id="{disp_id}"]').click()
page.locator(f'[data-action="select-period"][data-period-id="{period_a}"]').click()
page.wait_for_selector("#recipesList .list-item", timeout=10000)
assert list_dom_recipe_ids(page_a) == [r1, r2]
assert list_dom_recipe_ids(page_b) == [r1, r2]
drag_reorder_recipe(page_a, r1, direction="down")
page_a.wait_for_timeout(600)
from tests.e2e.dual_terminal_conftest import sync_both
sync_both(dual_harness)
page_b.reload()
page_b.wait_for_selector("#recipesDashboard", timeout=15000)
page_b.locator(f'[data-action="select-dispenser"][data-dispenser-id="{disp_id}"]').click()
page_b.locator(f'[data-action="select-period"][data-period-id="{period_a}"]').click()
page_b.wait_for_timeout(500)
assert period_recipe_ids(page_a, live_server_a_url, period_a) == [r2, r1]
assert period_recipe_ids(page_b, live_server_b_url, period_a) == [r2, r1]
def test_dual_edit_recipe_name_both_see(
page_a, page_b, dual_harness, live_server_a_url, live_server_b_url
) -> None:
r1 = dual_harness._e2e_r1 # type: ignore[attr-defined]
current = page_a.request.get(f"{live_server_a_url}/api/recipes/{r1}")
assert current.ok
payload = current.json()
payload["name"] = "Dual renamed"
payload["ingredients"] = payload.get("ingredients") or []
payload["unloading_groups"] = payload.get("unloading_groups") or []
put = page_a.request.put(f"{live_server_a_url}/api/recipes/{r1}", data=payload)
assert put.ok, put.text()
dual_harness.push_from_terminal("a")
with dual_harness.server_ctx():
from app import db
from app.models import Recipe
from app.services.sync_manager import enqueue_sync_queue_task
row = db.session.get(Recipe, r1)
if row is not None:
row.name = "Dual renamed"
db.session.commit()
enqueue_sync_queue_task("recipe", r1, "update", priority=2)
db.session.commit()
from tests.e2e.dual_terminal_conftest import sync_both
sync_both(dual_harness)
for page, url in ((page_a, live_server_a_url), (page_b, live_server_b_url)):
resp = page.request.get(f"{url}/api/recipes/{r1}")
assert resp.ok
assert resp.json().get("name") == "Dual renamed"
def test_dual_copy_paste_unloading_groups(
page_a, dual_harness, live_server_a_url, live_server_b_url, page_b
) -> None:
"""После paste на A sync — B видит рецепт в period B (API)."""
period_b = dual_harness._e2e_period_b # type: ignore[attr-defined]
r1 = dual_harness._e2e_r1 # type: ignore[attr-defined]
src = page_a.request.get(f"{live_server_a_url}/api/recipes/{r1}")
assert src.ok
body = src.json()
body["name"] = f"{body.get('name', 'R')} (копия)"
body["ingredients"] = body.get("ingredients") or []
body["unloading_groups"] = body.get("unloading_groups") or [
{"name": "G1", "distribution_type": "percent", "value": 100, "order": 1}
]
create = page_a.request.post(
f"{live_server_a_url}/api/periods/{period_b}/recipes",
data=body,
)
assert create.ok or create.status in (200, 201), create.text()
new_id = create.json().get("id") if create.ok else None
dual_harness.push_from_terminal("a")
if new_id:
with dual_harness.server_ctx():
from app.services.sync_manager import enqueue_sync_queue_task
enqueue_sync_queue_task("recipe", new_id, "create", priority=2)
enqueue_sync_queue_task(
"period_recipes", f"{period_b}:{new_id}", "create", priority=2
)
from app import db
db.session.commit()
from tests.e2e.dual_terminal_conftest import sync_both
sync_both(dual_harness)
listed = page_b.request.get(f"{live_server_b_url}/api/periods/{period_b}/recipes")
assert listed.ok
assert len(listed.json()) >= 1
rid = new_id or listed.json()[0]["id"]
detail = page_b.request.get(f"{live_server_b_url}/api/recipes/{rid}")
assert detail.ok
groups = detail.json().get("unloading_groups") or []
assert groups
def test_dual_transfer_then_reorder_on_b(
page_a, page_b, dual_harness, live_server_a_url, live_server_b_url
) -> None:
SCENARIO_DUAL_E2E_TRANSFER_REORDER # noqa: F841
disp_id = dual_harness._e2e_disp_id # type: ignore[attr-defined]
period_a = dual_harness._e2e_period_a # type: ignore[attr-defined]
period_b = dual_harness._e2e_period_b # type: ignore[attr-defined]
r2 = dual_harness._e2e_r2 # type: ignore[attr-defined]
from tests.e2e.recipes_e2e_helpers import drag_transfer_to_period
page_a.locator(f'[data-action="select-dispenser"][data-dispenser-id="{disp_id}"]').click()
page_a.locator(f'[data-action="select-period"][data-period-id="{period_a}"]').click()
drag_transfer_to_period(page_a, r2, period_b)
from tests.e2e.dual_terminal_conftest import sync_both
sync_both(dual_harness)
page_b.locator(f'[data-action="select-dispenser"][data-dispenser-id="{disp_id}"]').click()
page_b.locator(f'[data-action="select-period"][data-period-id="{period_b}"]').click()
ids_b = period_recipe_ids(page_b, live_server_b_url, period_b)
assert r2 in ids_b