# This is an unexhaustive test suite to demonstrate basic use of whaack's topo.py

from topo import new_vpatch, new_filemetadata, topo_sort_vpatches

# This is the information that would be extracted from a vpatch file's
# --- /path/to/file file_hash
# +++ /path/to/file file_hash
# lines.
# A full V would also need the information describing the actual file changes included.
f1 = new_filemetadata('a.txt', 'false')
f2 = new_filemetadata('a.txt', 'e1c112ff908febc3b98b1693a6cd3564eaf8e5e6ca629d084d9f0eba99247cacdd72e369ff8941397c2807409ff66be64be908da17ad7b8a49a2a26c0e8086aa')
f3 = new_filemetadata('a.txt', '1c5ac2e083b47ac286de79815c8d21b44764b4e00f18bfdc41f789d53ac47302623c7b9dade4e970a78a894dfcf45f0c671401cfc866eeaba8804090a50e134e')
f4 = new_filemetadata('b.txt', 'false')
f5 = new_filemetadata('b.txt', '799ef7a37eac7d4e29ed4c6b6fe3ffd4ef0be447cdd4a63eedd1411f260d6789ef74ab43010ada249f40faefd87557c719c075bdebac6ff8128d8be5e471b292')
f6 = new_filemetadata('a.txt', '0cc673a90f1ace755ab84d73e45096e302856d183e7ad8ff6bdee9e9f7183b4baf8b38049ba91054a252cbd94729d775227501603e3ed799b47ae15c10d39cc9')

vp1 = new_vpatch('genesis', (f1,), (f2,))
assert(topo_sort_vpatches((vp1,)) == (vp1,))

vp2 = new_vpatch('patch1', (f2,), (f3,))
assert(topo_sort_vpatches((vp2, vp1)) == (vp1, vp2))

# Make sure we raise an error on cyclic graphs.
vp3 = new_vpatch('patch2', (f3,), (f2,))
try:
    topo_sort_vpatches((vp2, vp1, vp3))
    # Note that this exception will be caught, but the assertion within our except clauses
    # makes sure that the exception through is the Cyclic Graph exception.
    assert(False)
except Exception as e:
    assert(str(e) == 'Cyclic Graph')

# Test that deleting a file does not cause a cyclic graph error.
vp4 = new_vpatch('patch3', (f3, f4), (f1, f5))
assert(topo_sort_vpatches((vp4, vp1, vp2)) == (vp1, vp2, vp4))

# Test that a vtree with nodes that have more than one children correctly sorts.
vp5 = new_vpatch('patch4', (f2,), (f6,))
topo_sorted_4125 = topo_sort_vpatches((vp4, vp1, vp2, vp5))
assert(topo_sorted_4125.index(vp1) == 0)
assert(topo_sorted_4125.index(vp2) > topo_sorted_4125.index(vp1))
assert(topo_sorted_4125.index(vp5) > topo_sorted_4125.index(vp1))
assert(topo_sorted_4125.index(vp4) > topo_sorted_4125.index(vp2))
