#!/usr/bin/env python
import coral
from coral import modeler
from coral.modeler.modeler import *
from coral.modeler.diagram import xmidi_diagrams
from coral.modeler.diagram.degen import searchForSimpleGraphNode
from coral.modeler import xmidigraphbuilder


# This test checks that we can handle several xmidi graphedges
# in the same diagram that all are linked to the same abstract
# element. It also checks that we do not create too many graphconnectors,
# and that sychronization does not leave any orphaned graphconnectors
# behind.

m=ModelerWindow()
m.main(loop=0)

L = coral.lang.UML14
DI = coral.lang.XMIDI20

tm = coral.getTransactionManager()

tm.beginModifyCmd()
try:
    prj=coral.Project()
    
    model = L.Model()
    model.__setProject__(prj)
    c1 = L.Class(namespace=model)
    c2 = L.Class(namespace=model)
    c3 = L.Class(namespace=model)
    d1 = L.Dependency(namespace=model, client=[c1], supplier=[c2])
    ## Create a ClassDiagram from the model
    cd = xmidi_diagrams.createDiagram(prj,owner_elem=model,typeinfo="ClassDiagram")
    assert cd
    xmidigraphbuilder.xmidibuilder(model, cd) 
finally:
    tm.endModifyCmd()

# Check that the diagram is ok

assert len(c1.xmidi_get_graphelements()) == 1
x_c1 = c1.xmidi_get_graphelements()[0]

assert x_c1
assert len(x_c1.anchorage) == 1

assert len(c2.xmidi_get_graphelements()) == 1
x_c2 = c2.xmidi_get_graphelements()[0]

assert x_c2
assert len(x_c2.anchorage) == 1

assert len(c3.xmidi_get_graphelements()) == 1
x_c3 = c3.xmidi_get_graphelements()[0]

assert x_c3
assert len(x_c3.anchorage) == 0

assert len(d1.xmidi_get_graphelements()) == 1
x_d1 = d1.xmidi_get_graphelements()[0]

# Check the graphconnectors are ok

assert x_d1
assert len(x_d1.anchor) == 2
assert len(x_c1.anchorage) == 1
assert len(x_c2.anchorage) == 1
assert len(x_c3.anchorage) == 0
assert x_d1.anchor[0].graphElement == x_c1
assert x_d1.anchor[1].graphElement == x_c2

# Create one more representation of the edge
tm.beginModifyCmd()
try:
    xmidigraphbuilder.xmidibuilder_myself_also(d1, cd)
finally:
    tm.endModifyCmd()

# Check the numbers of graphelements are ok
assert len(c1.xmidi_get_graphelements()) == 1
assert len(c2.xmidi_get_graphelements()) == 1
assert len(c3.xmidi_get_graphelements()) == 1
assert len(d1.xmidi_get_graphelements()) == 2


x_d1s = d1.xmidi_get_graphelements()
# Check that each edge has connectors to the right graphnodes
for di in x_d1s:
    assert len(di.anchor) == 2
    assert di.anchor[0].graphElement == x_c1
    assert di.anchor[1].graphElement == x_c2

# Check that xmibuilder through attachGraphConnectors create only the
# necessary graphconnectors
assert len(x_c1.anchorage) == 2
assert len(x_c2.anchorage) == 2
assert len(x_c3.anchorage) == 0

# Create a third graphedge
tm.beginModifyCmd()
try:
    xmidigraphbuilder.xmidibuilder_myself_also(d1, cd)
finally:
    tm.endModifyCmd()

# Check the numbers of graphelements are ok
assert len(c1.xmidi_get_graphelements()) == 1
assert len(c2.xmidi_get_graphelements()) == 1
assert len(c3.xmidi_get_graphelements()) == 1
assert len(d1.xmidi_get_graphelements()) == 3


x_d1s = d1.xmidi_get_graphelements()
# Check that each edge has connectors to the right graphnodes
for di in x_d1s:
    assert len(di.anchor) == 2
    assert di.anchor[0].graphElement == x_c1
    assert di.anchor[1].graphElement == x_c2

# Check that xmibuilder through attachGraphConnectors create only the
# necessary graphconnectors
assert len(x_c1.anchorage) == 3
assert len(x_c2.anchorage) == 3
assert len(x_c3.anchorage) == 0


# relink d1.supplier from c2 to c3
tm.beginModifyCmd()
try:
    d1.supplier = [c3]
finally:
    tm.endModifyCmd()


x_d1s = d1.xmidi_get_graphelements()
# Check that each edge has connectors to the right graphnodes
for di in x_d1s:
    assert len(di.anchor) == 2
    assert di.anchor[0].graphElement == x_c1
    assert di.anchor[1].graphElement == x_c3

# Check that the synchronization does not leave old connectors
# and that all graphedges are relinked
assert len(x_c1.anchorage) == 3
assert len(x_c2.anchorage) == 0
assert len(x_c3.anchorage) == 3


# relink d1.client from c1 to c2
tm.beginModifyCmd()
try:
    d1.client = [c2]
finally:
    tm.endModifyCmd()


x_d1s = d1.xmidi_get_graphelements()
# Check that each edge has connectors to the right graphnodes
for di in x_d1s:
    assert len(di.anchor) == 2
    assert di.anchor[0].graphElement == x_c2
    assert di.anchor[1].graphElement == x_c3

# Check that the synchronization does not leave old connectors
# and that all graphedges are relinked
assert len(x_c1.anchorage) == 0
assert len(x_c2.anchorage) == 3
assert len(x_c3.anchorage) == 3


# Finally, relink d1.client to c3
tm.beginModifyCmd()
try:
    d1.client = [c3]
finally:
    tm.endModifyCmd()


x_d1s = d1.xmidi_get_graphelements()
# Check that each edge has connectors to the right graphnodes
for di in x_d1s:
    assert len(di.anchor) == 2
    assert di.anchor[0].graphElement == x_c3
    assert di.anchor[1].graphElement == x_c3

# Check that the synchronization does not leave old connectors
# and that all graphedges are relinked
assert len(x_c1.anchorage) == 0
assert len(x_c2.anchorage) == 0
assert len(x_c3.anchorage) == 6


