126 lines
4.6 KiB
Python
126 lines
4.6 KiB
Python
"""Tests E2E de la pagination de la recherche (recherche.php).
|
|
|
|
La pagination est déléguée à l'API PeerTube (paramètre start) et le total
|
|
affiché est le total réel renvoyé par l'API — et non le nombre de vidéos
|
|
réellement présentes sur la page.
|
|
"""
|
|
import json
|
|
import math
|
|
import re
|
|
import urllib.parse
|
|
import urllib.request
|
|
|
|
import pytest
|
|
|
|
VIDEOS_PAR_PAGE = 12 # VIDEOS_PER_PAGE (includes/config.default.php)
|
|
TERMES_CANDIDATS = ["a", "e", "video", "les"]
|
|
|
|
|
|
def _total_api(peertube_url, terme):
|
|
"""Total d'une recherche plein texte côté API PeerTube."""
|
|
params = urllib.parse.urlencode({
|
|
"search": terme,
|
|
"isLocal": "true",
|
|
"count": 1,
|
|
})
|
|
url = f"{peertube_url}/api/v1/search/videos?{params}"
|
|
with urllib.request.urlopen(url, timeout=30) as rep:
|
|
return int(json.load(rep).get("total", 0))
|
|
|
|
|
|
def _nombre_resultats(page):
|
|
"""Extrait le total affiché dans le bandeau des résultats."""
|
|
texte = page.locator(".search-results-count p").inner_text()
|
|
m = re.search(r"(\d+)", texte)
|
|
assert m, f"Total introuvable dans le bandeau : {texte!r}"
|
|
return int(m.group(1))
|
|
|
|
|
|
def _ids_cartes(page):
|
|
"""Identifiants des vidéos affichées dans la grille de résultats."""
|
|
cartes = page.locator(".video-grid .video-card")
|
|
return {
|
|
cartes.nth(i).get_attribute("data-video-id")
|
|
for i in range(cartes.count())
|
|
}
|
|
|
|
|
|
@pytest.fixture(scope="session")
|
|
def terme_paginable(peertube_url):
|
|
"""Un terme de recherche couvrant au moins deux pages de résultats."""
|
|
for terme in TERMES_CANDIDATS:
|
|
try:
|
|
if _total_api(peertube_url, terme) > VIDEOS_PAR_PAGE:
|
|
return terme
|
|
except Exception:
|
|
continue
|
|
pytest.skip("Aucun terme avec plus d'une page de résultats (réseau ?)")
|
|
|
|
|
|
def test_recherche_affiche_total_reel(page, base_url, peertube_url, terme_paginable):
|
|
"""Le total affiché est le total réel de l'API, pas le contenu de la page."""
|
|
total_api = _total_api(peertube_url, terme_paginable)
|
|
page.goto(
|
|
f"{base_url}/recherche.php?q={urllib.parse.quote(terme_paginable)}",
|
|
wait_until="domcontentloaded",
|
|
)
|
|
|
|
cartes = page.locator(".video-grid .video-card")
|
|
if cartes.count() == 0:
|
|
pytest.skip("Aucune vidéo reçue de l'API PeerTube (réseau indisponible ?)")
|
|
|
|
total_affiche = _nombre_resultats(page)
|
|
assert total_affiche == total_api
|
|
# La première page ne contient qu'une page de résultats, pas le total
|
|
assert total_affiche > cartes.count()
|
|
assert cartes.count() == min(VIDEOS_PAR_PAGE, total_affiche)
|
|
|
|
# La barre de pagination reflète le total réel
|
|
assert page.locator(".pagination").count() == 1
|
|
assert page.locator(".page-number.current").inner_text() == "1"
|
|
numeros = [
|
|
int(page.locator(".page-number").nth(i).inner_text())
|
|
for i in range(page.locator(".page-number").count())
|
|
]
|
|
assert max(numeros) == math.ceil(total_affiche / VIDEOS_PAR_PAGE)
|
|
|
|
|
|
def test_recherche_navigation_page_2(page, base_url, terme_paginable):
|
|
"""Le lien « Suivant » mène à la page 2, avec des vidéos différentes."""
|
|
page.goto(
|
|
f"{base_url}/recherche.php?q={urllib.parse.quote(terme_paginable)}",
|
|
wait_until="domcontentloaded",
|
|
)
|
|
ids_page1 = _ids_cartes(page)
|
|
if not ids_page1:
|
|
pytest.skip("Aucune vidéo reçue de l'API PeerTube (réseau indisponible ?)")
|
|
|
|
page.locator(".page-link.next").click()
|
|
page.wait_for_url(re.compile(r"[?&]page=2(&|$)"))
|
|
|
|
assert page.locator(".page-number.current").inner_text() == "2"
|
|
assert page.locator(".page-link.prev").count() == 1
|
|
|
|
ids_page2 = _ids_cartes(page)
|
|
assert ids_page2, "La page 2 ne contient aucune vidéo"
|
|
assert ids_page2.isdisjoint(ids_page1), "Les pages 1 et 2 partagent des vidéos"
|
|
|
|
|
|
def test_recherche_page_hors_limites(page, base_url, terme_paginable):
|
|
"""Une page au-delà de la dernière retombe sur une page valide."""
|
|
page.goto(
|
|
f"{base_url}/recherche.php?q={urllib.parse.quote(terme_paginable)}&page=99999999",
|
|
wait_until="domcontentloaded",
|
|
)
|
|
|
|
cartes = page.locator(".video-grid .video-card")
|
|
if cartes.count() == 0:
|
|
pytest.skip("Aucune vidéo reçue de l'API PeerTube (réseau indisponible ?)")
|
|
|
|
# La page se rabat sur une page valide (jamais de grille vide ni d'erreur)
|
|
total_affiche = _nombre_resultats(page)
|
|
assert total_affiche > 0
|
|
assert page.locator(".page-number.current").count() == 1
|
|
page_courante = int(page.locator(".page-number.current").inner_text())
|
|
assert 1 <= page_courante <= math.ceil(total_affiche / VIDEOS_PAR_PAGE)
|