local tests = require("Module:UnitTests")
local m_accent = require("Module:grc-accent")
local m_utilities = require("Module:grc-utilities")
local m_table = require("Module:table")
local tag = m_utilities.tag
local compose = mw.ustring.toNFC
function tests:check_mark_implied_length(example, expected)
self:equals(
tag(example),
compose(m_accent.mark_implied_length(example)),
compose(expected),
{ display = tag }
)
end
function tests:check_length_at(example, position, expected)
self:equals(
tag(example) .. " (" .. position .. " syllables from end)",
m_accent.length_at(example, position),
expected
)
end
function tests:check_get_length(example, expected, is_noun)
local lengths = {}
local get_length = m_accent.get_length
local tokens = m_utilities.tokenize(example)
local token_count = #tokens
local short_diphthong = is_noun
for i, token in m_table.reverseIpairs(tokens) do
if m_accent.contains_vowel(token) then
if i ~= token_count then
short_diphthong = false
end
table.insert(lengths, get_length(token, short_diphthong))
end
end
lengths = m_table.reverseConcat(lengths, ", ")
self:equals(
tag(example),
lengths,
expected
)
end
function tests:check_harmonize_length(word1, word2, expected)
self:equals(
tag(word1 .. ", " .. word2),
compose(table.concat({ m_accent.harmonize_length(word1, word2) }, ", ")),
compose(expected),
{ display = tag }
)
end
function tests:check_strip_accent(example, expected)
self:equals(
tag(example),
compose(m_accent.strip_accent(example)),
compose(expected),
{ display = tag }
)
end
function tests:check_strip_tone(example, expected)
self:equals(
tag(example),
compose(m_accent.strip_tone(example)),
compose(expected),
{ display = tag }
)
end
function tests:check_get_weight(example, expected, position)
self:equals(
tag(example) .. " (" .. position .. ")",
m_accent.get_weight(example, position),
expected
)
self:equals(
tag(example),
m_accent.get_weight(example),
expected
)
end
function tests:check_add_accent(example, position, expected, circumflex, is_noun)
self:equals(
tag(example) .. " (" .. m_table.sparseConcat({ position, circumflex and "circumflex" or nil, is_noun and "noun" or nil }, ", ") .. ")",
compose(m_accent.add_accent(example, position, { short_diphthong = is_noun, synaeresis = is_noun, circumflex = circumflex })),
compose(expected),
{ display = tag }
)
end
local function display_detect_accent(syllable, accent_name)
return syllable .. ", " .. accent_name
end
function tests:check_detect_accent(example, expected, from_end)
self:equals(
tag(example) .. (from_end and " (from end)" or ""),
display_detect_accent(m_accent.detect_accent(example, from_end)),
expected
)
end
function tests:check_get_accent_term(example, expected)
self:equals(
tag(example),
m_accent.get_accent_term(example),
expected
)
end
function tests:test_mark_implied_length()
local examples = {
{ "μοῖρα", "μοῖρᾰ" },
{ "χώρα", "χώρᾱ" },
{ "πάθος", "πᾰ́θος" },
{ "ἀλήθεια", "ἀλήθειᾰ" },
}
tests:iterate(examples, "check_mark_implied_length")
end
function tests:test_length_at()
local examples = {
{ "μοῖρα", 2, "long" },
{ "πάθους", 2, "either" },
{ "πᾰ́θος", 2, "short" },
}
tests:iterate(examples, "check_length_at")
end
function tests:test_get_length()
local examples = {
"ambiguous vowels",
{ "αἷμᾰ", "long, short", true },
{ "μοῖρα", "long, either" },
{ "πάθος", "either, short" },
{ "πᾰ́θος", "short, short" },
{ "ἆρᾰ", "long, short" },
"capital letters",
{ "ᾍδης", "long, long" },
{ "Αἰσχύλος", "long, either, short" },
{ "Ἠλέκτρᾱ", "long, short, long" },
{ "Ἑλλάς", "short, either" },
"short final diphthongs",
{ "ᾰ̓λήθειαι", "short, long, long, short", true },
{ "Ᾰ̓θηναιοι", "short, long, long, short", true },
{ "Ᾰ̓θηναίοιν", "short, long, long, long", true },
{ "Ᾰ̓θηναίοις", "short, long, long, long", true },
}
tests:iterate(examples, "check_get_length")
end
function tests:test_harmonize_length()
local examples = {
{ "ᾰ̓́λοξ", "ἄλοκος", "ᾰ̓́λοξ, ᾰ̓́λοκος" },
{ "ἄλοκος", "ᾰ̓́λοξ", "ᾰ̓́λοκος, ᾰ̓́λοξ" },
{ "ἄλοξ", "ἄλοκος", "ᾰ̓́λοξ, ᾰ̓́λοκος" },
{ "Αἰθίοψ", "Αἰθίοπος", "Αἰθῐ́οψ, Αἰθῐ́οπος" },
"transfer length only if both vowels have the same breathing mark",
{ "ἄξιος", "ᾱ", "ἄξιος, ᾱ" },
}
tests:iterate(examples, "check_harmonize_length")
end
function tests:test_strip_accent()
local examples = {
{ "ᾰ̓́νθρωπος", "ανθρωπος" },
{ "Πηληῐ̈ᾰ́δης", "Πηληιαδης" },
-- { },
}
tests:iterate(examples, "check_strip_accent")
end
function tests:test_strip_tone()
local examples = {
{ "Πηληῐ̈ᾰ́δης", "Πηληῐ̈ᾰδης" },
{ "Ᾱ̔́ͅδης", "Ᾱ̔ͅδης" }, -- pleonastic
{ "μολὼν λαβέ", "μολων λαβε" },
"circumflex → macron",
{ "πᾶς", "πᾱς" },
"circumflexes on diphthongs should not<br>be replaced with macrons",
{ "οἷαι", "οἱαι" }, -- οῑαι if tokenization yields ο-ῑαι
{ "γᾰλεοῦ", "γᾰλεου" }, -- γᾰλεοῡ if tokenization yields γᾰλεο-ῦ
}
tests:iterate(examples, "check_strip_tone")
end
function tests:test_get_weight()
local examples = {
{ "ὀρθ", "heavy", 1 },
{ "μικρ", "heavy", 1 },
{ "ἰδι", nil, 1 },
{ "ῐ̓δῐ", "light", 1 },
{ "φῐλ", "light", 1 },
}
tests:iterate(examples, "check_get_weight")
end
function tests:test_add_accent()
local examples = {
{ "κρεως", 1, "κρέως", nil, true},
{ "Τρως", 1, "Τρώς", nil, true },
{ "πολεως", 1, "πόλεως", nil, true },
{ "πολεων", 1, "πόλεων", nil, true },
{ "Πειριθοι", 2, "Πειρίθοι", nil, true },
{ "Ᾰ̓θηναιοιν", -2, "Ᾰ̓θηναίοιν", nil, true },
{ "Ᾰ̓θηναιοις", -2, "Ᾰ̓θηναίοις", nil, true },
{ "βᾰρειαι", -2, "βᾰρεῖαι", nil, true },
{ "ᾰ̓ληθειαι", -3, "ᾰ̓λήθειαι", nil, true },
{ "Ᾰ̓θηναιοι", 3, "Ᾰ̓θηναῖοι", nil, true },
{ "βᾰρειαι", 2, "βᾰρεῖαι", nil, true },
{ "ᾰ̓ληθειαι", 2, "ᾰ̓λήθειαι", nil, true },
{ "αἱμᾰ", 1, "αἷμᾰ", nil, true },
{ "λογος", -2, "λόγος" },
{ "προτερᾱ", -3, "προτέρᾱ" },
{ "Αἰθιοπων", 2, "Αἰθιόπων"}, -- position 2 because the nominative is Αἰθίοψ
{ "χωρῶν", 1, "χωρῶν"}, -- don't modify existing accent
{ "δημος", 1, "δῆμος" },
{ "τοιουτος", 2, "τοιοῦτος" },
{ "χωρᾱ", 1, "χώρᾱ" },
{ "μοιρᾰ", 1, "μοῖρᾰ" },
{ "προτερᾱ", 1, "προτέρᾱ" },
{ "ἐγενετο", 1, "ἐγένετο" },
{ "φως", 1, "φῶς", true },
{ "μοιρα", 1, "μοίρα" },
{ "μοιρα", 1, "μοῖρα", true },
{ "ἐγενετο", 1, "ἐγένετο", true },
{ "λογος", 1, "λόγος" },
{ "λογος", 1, "λόγος", true },
}
tests:iterate(examples, "check_add_accent")
end
function tests:test_detect_accent()
local examples = {
{ "ἐγένετο", "2, acute" },
{ "ἐγένετο", "3, acute", true },
{ "τοιοῦτος", "2, circumflex" },
{ "τοιοῦτος", "2, circumflex", true },
{ "φῶς", "1, circumflex" },
{ "φῶς", "1, circumflex", true },
}
tests:iterate(examples, "check_detect_accent")
end
function tests:test_get_accent_term()
local examples = {
{ "πολὺς", "barytone" },
{ "πολύς", "oxytone" },
{ "λέγω", "paroxytone" },
{ "γίγνομαι", "proparoxytone" },
{ "φῶς", "perispomenon" },
{ "οἷος", "properispomenon" },
}
tests:iterate(examples, "check_get_accent_term")
end
return tests