forked from retoor/devplacepy
chore: reorganize test files into domain-specific subdirectories under tests/
Split the monolithic test directory into three tiers (unit, api, e2e) with a path-mirroring directory structure. Added corresponding Makefile targets (test-unit, test-api, test-e2e) and updated all documentation references (CLAUDE.md, README.md, testing-cicd.html, testing-framework.html, testing-make.html) to reflect the new layout and naming conventions.
This commit is contained in:
@@ -0,0 +1,201 @@
|
||||
# retoor <retoor@molodetz.nl>
|
||||
|
||||
from datetime import datetime, timezone
|
||||
from devplacepy.database import (
|
||||
get_table,
|
||||
get_users_by_uids,
|
||||
get_vote_counts,
|
||||
get_user_votes,
|
||||
get_comment_counts_by_post_uids,
|
||||
resolve_by_slug,
|
||||
get_user_stars,
|
||||
get_user_rank,
|
||||
build_pagination,
|
||||
)
|
||||
from devplacepy.utils import generate_uid
|
||||
def _now_db_helpers():
|
||||
return datetime.now(timezone.utc).isoformat()
|
||||
def _user_db_helpers():
|
||||
uid = generate_uid()
|
||||
get_table("users").insert(
|
||||
{
|
||||
"uid": uid,
|
||||
"username": f"dbh_{uid[:8]}",
|
||||
"email": f"{uid[:8]}@t.dev",
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
return uid
|
||||
def _post(owner, **extra):
|
||||
uid = generate_uid()
|
||||
get_table("posts").insert(
|
||||
{
|
||||
"uid": uid,
|
||||
"user_uid": owner,
|
||||
"slug": f"{uid[:8]}-post",
|
||||
"title": None,
|
||||
"content": "db helper post body",
|
||||
"topic": "random",
|
||||
"project_uid": None,
|
||||
"image": None,
|
||||
"stars": 0,
|
||||
"created_at": _now_db_helpers(),
|
||||
**extra,
|
||||
}
|
||||
)
|
||||
return uid
|
||||
def _comment(owner, target_uid):
|
||||
uid = generate_uid()
|
||||
get_table("comments").insert(
|
||||
{
|
||||
"uid": uid,
|
||||
"user_uid": owner,
|
||||
"target_uid": target_uid,
|
||||
"target_type": "post",
|
||||
"content": "db helper comment",
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
return uid
|
||||
def _vote(target_type, target_uid, value):
|
||||
get_table("votes").insert(
|
||||
{
|
||||
"uid": generate_uid(),
|
||||
"user_uid": generate_uid(),
|
||||
"target_uid": target_uid,
|
||||
"target_type": target_type,
|
||||
"value": value,
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
from uuid import uuid4
|
||||
from tests.conftest import BASE_URL
|
||||
from devplacepy.database import get_table
|
||||
|
||||
|
||||
def test_get_users_by_uids_dedupes(local_db):
|
||||
a, b = generate_uid(), generate_uid()
|
||||
users = get_table("users")
|
||||
users.insert({"uid": a, "username": f"u_{a[:6]}", "created_at": _now_db_helpers()})
|
||||
users.insert({"uid": b, "username": f"u_{b[:6]}", "created_at": _now_db_helpers()})
|
||||
result = get_users_by_uids([a, b, a])
|
||||
assert set(result.keys()) == {a, b}
|
||||
|
||||
|
||||
def test_get_vote_counts_groups_up_and_down(local_db):
|
||||
target = generate_uid()
|
||||
votes = get_table("votes")
|
||||
for value in (1, 1, -1):
|
||||
votes.insert(
|
||||
{
|
||||
"uid": generate_uid(),
|
||||
"user_uid": generate_uid(),
|
||||
"target_uid": target,
|
||||
"target_type": "post",
|
||||
"value": value,
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
ups, downs = get_vote_counts([target])
|
||||
assert ups[target] == 2
|
||||
assert downs[target] == 1
|
||||
|
||||
|
||||
def test_get_user_votes_returns_user_value(local_db):
|
||||
target = generate_uid()
|
||||
user = generate_uid()
|
||||
get_table("votes").insert(
|
||||
{
|
||||
"uid": generate_uid(),
|
||||
"user_uid": user,
|
||||
"target_uid": target,
|
||||
"target_type": "post",
|
||||
"value": 1,
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
assert get_user_votes(user, [target]) == {target: 1}
|
||||
|
||||
|
||||
def test_get_comment_counts_by_post_uids(local_db):
|
||||
post = generate_uid()
|
||||
comments = get_table("comments")
|
||||
for _ in range(2):
|
||||
comments.insert(
|
||||
{
|
||||
"uid": generate_uid(),
|
||||
"user_uid": generate_uid(),
|
||||
"target_type": "post",
|
||||
"target_uid": post,
|
||||
"content": "hi",
|
||||
"created_at": _now_db_helpers(),
|
||||
}
|
||||
)
|
||||
assert get_comment_counts_by_post_uids([post]) == {post: 2}
|
||||
|
||||
|
||||
def test_resolve_by_slug_finds_by_slug_or_uid(local_db):
|
||||
owner = _user_db_helpers()
|
||||
uid = _post(owner)
|
||||
posts = get_table("posts")
|
||||
slug = posts.find_one(uid=uid)["slug"]
|
||||
assert resolve_by_slug(posts, slug)["uid"] == uid
|
||||
assert resolve_by_slug(posts, uid)["uid"] == uid
|
||||
assert resolve_by_slug(posts, "missing-slug-xyz") is None
|
||||
|
||||
|
||||
def test_get_user_stars_counts_all_votable_contributions(local_db):
|
||||
user = _user_db_helpers()
|
||||
post_uid = _post(user)
|
||||
for _ in range(7):
|
||||
_vote("post", post_uid, 1)
|
||||
comment_uid = _comment(user, post_uid)
|
||||
_vote("comment", comment_uid, 1)
|
||||
_vote("comment", comment_uid, 1)
|
||||
_vote("comment", comment_uid, -1)
|
||||
assert get_user_stars(user) == 8
|
||||
|
||||
|
||||
def test_get_user_rank_unknown_user_is_none(local_db):
|
||||
assert get_user_rank(generate_uid()) is None
|
||||
|
||||
|
||||
def test_build_pagination_metadata():
|
||||
first = build_pagination(1, 100, 25)
|
||||
assert first["total_pages"] == 4
|
||||
assert first["has_prev"] is False
|
||||
assert first["has_next"] is True
|
||||
middle = build_pagination(2, 100, 25)
|
||||
assert middle["has_prev"] is True
|
||||
assert middle["has_next"] is True
|
||||
clamped = build_pagination(99, 10, 25)
|
||||
assert clamped["page"] == 1
|
||||
assert clamped["total_pages"] == 1
|
||||
|
||||
|
||||
def test_diversify_by_author_caps_per_author():
|
||||
from devplacepy.database import diversify_by_author
|
||||
|
||||
rows = [
|
||||
{"uid": 1, "user_uid": "a"},
|
||||
{"uid": 2, "user_uid": "a"},
|
||||
{"uid": 3, "user_uid": "a"},
|
||||
{"uid": 4, "user_uid": "b"},
|
||||
{"uid": 5, "user_uid": "a"},
|
||||
{"uid": 6, "user_uid": "c"},
|
||||
]
|
||||
kept = diversify_by_author(rows, max_per_author=2, limit=6)
|
||||
authors = [r["user_uid"] for r in kept]
|
||||
assert authors.count("a") == 2
|
||||
assert authors.count("b") == 1
|
||||
assert authors.count("c") == 1
|
||||
assert [r["uid"] for r in kept] == [1, 2, 4, 6]
|
||||
|
||||
|
||||
def test_diversify_by_author_respects_limit():
|
||||
from devplacepy.database import diversify_by_author
|
||||
|
||||
rows = [{"uid": i, "user_uid": str(i)} for i in range(10)]
|
||||
kept = diversify_by_author(rows, max_per_author=2, limit=3)
|
||||
assert len(kept) == 3
|
||||
assert [r["uid"] for r in kept] == [0, 1, 2]
|
||||
Reference in New Issue
Block a user