feat(reader): multi-word and phrasal verb detector in reader (Task 14)
This commit is contained in:
1 parent
37a1f1ab35
commit
1c3f03a64c
9 files changed
+738
-16
No files matched your search
@@ -1271,4 +1271,93 @@ def test_sentence_translation_ai_and_caching():
|
||||
assert "active_model" in status_data
|
||||
|
||||
|
||||
def test_phrasal_verb_detector_unit_and_integration():
|
||||
"""Validates phrasal verb lemmatization, context detection, separable verbs, and API integration."""
|
||||
from app.phrasal import lemmatize_word, detect_phrasal_verb
|
||||
|
||||
# 1. Lemmatization tests
|
||||
assert "take" in lemmatize_word("took")
|
||||
assert "give" in lemmatize_word("giving")
|
||||
assert "figure" in lemmatize_word("figured")
|
||||
assert "run" in lemmatize_word("running")
|
||||
|
||||
# 2. Direct unit detection tests
|
||||
# Contiguous 2-word phrasal verb: clicking verb or particle
|
||||
res_verb = detect_phrasal_verb("The plane took off into the sky.", "took")
|
||||
assert res_verb is not None
|
||||
assert res_verb["term"] == "take off"
|
||||
assert res_verb["raw"] == "took off"
|
||||
assert res_verb["separable"] is False
|
||||
|
||||
res_part = detect_phrasal_verb("The plane took off into the sky.", "off")
|
||||
assert res_part is not None
|
||||
assert res_part["term"] == "take off"
|
||||
|
||||
# Contiguous 3-word phrasal verb
|
||||
res_triple = detect_phrasal_verb("She came up with a great solution.", "came")
|
||||
assert res_triple is not None
|
||||
assert res_triple["term"] == "come up with"
|
||||
assert res_triple["raw"] == "came up with"
|
||||
|
||||
res_fwd = detect_phrasal_verb("I look forward to our trip.", "forward")
|
||||
assert res_fwd is not None
|
||||
assert res_fwd["term"] == "look forward to"
|
||||
|
||||
# Separable phrasal verb
|
||||
res_sep_v = detect_phrasal_verb("Please turn it off before leaving.", "turn")
|
||||
assert res_sep_v is not None
|
||||
assert res_sep_v["term"] == "turn off"
|
||||
assert res_sep_v["separable"] is True
|
||||
|
||||
res_sep_p = detect_phrasal_verb("Please turn it off before leaving.", "off")
|
||||
assert res_sep_p is not None
|
||||
assert res_sep_p["term"] == "turn off"
|
||||
assert res_sep_p["separable"] is True
|
||||
|
||||
# Negative case (no phrasal verb)
|
||||
res_none = detect_phrasal_verb("The red apple fell onto the soft grass.", "apple")
|
||||
assert res_none is None
|
||||
|
||||
# 3. HTTP Endpoint Integration
|
||||
client.cookies.clear()
|
||||
unauth = client.get("/api/detect-phrasal-verb?sentence=The+plane+took+off&word=took")
|
||||
assert unauth.status_code == 401
|
||||
|
||||
login_res = client.post("/api/login", json={"username": "testadmin", "password": "testpass12345"})
|
||||
assert login_res.status_code == 200
|
||||
|
||||
detect_res = client.get("/api/detect-phrasal-verb?sentence=The+plane+took+off&word=took")
|
||||
assert detect_res.status_code == 200
|
||||
data = detect_res.json()
|
||||
assert data["detected"] is True
|
||||
assert data["phrasal_verb"]["term"] == "take off"
|
||||
|
||||
# 4. Contextual integration inside /api/lookup
|
||||
lookup_res = client.get("/api/lookup?term=took&context=The+plane+took+off+into+the+sky")
|
||||
assert lookup_res.status_code == 200
|
||||
lookup_data = lookup_res.json()
|
||||
assert lookup_data["query"] == "took"
|
||||
assert lookup_data.get("phrasal_verb") is not None
|
||||
assert lookup_data["phrasal_verb"]["term"] == "take off"
|
||||
assert "взлетать" in lookup_data["phrasal_verb"]["translation"]
|
||||
assert lookup_data["phrasal_verb"]["in_library"] is False
|
||||
|
||||
# 5. In-library status check for phrasal verb
|
||||
add_card = client.post("/api/cards", json={
|
||||
"term": "take off",
|
||||
"translation": "взлетать, снимать",
|
||||
"context_sentence": "The plane took off into the sky.",
|
||||
"collection": "Фразовые глаголы & Идиомы",
|
||||
"tags": "phrasal-verbs, reader"
|
||||
})
|
||||
assert add_card.status_code == 200
|
||||
|
||||
lookup_after = client.get("/api/lookup?term=took&context=The+plane+took+off+into+the+sky")
|
||||
assert lookup_after.status_code == 200
|
||||
after_data = lookup_after.json()
|
||||
assert after_data["phrasal_verb"]["in_library"] is True
|
||||
assert after_data["phrasal_verb"]["library_card"] is not None
|
||||
|
||||
|
||||
|
||||
|
||||
Reference in new issue
Block a user