1#!/usr/bin/perl -w
2
3# Some basic GraphML tests
4
5use Test::More;
6use strict;
7use utf8;
8
9BEGIN
10   {
11   plan tests => 14;
12   chdir 't' if -d 't';
13   use lib '../lib';
14   use_ok ("Graph::Easy") or die($@);
15   use_ok ("Graph::Easy::Parser") or die($@);
16   };
17
18can_ok ('Graph::Easy', qw/
19  as_graphml
20  as_graphml_file
21  /);
22
23#############################################################################
24my $graph = Graph::Easy->new();
25
26my $graphml_file = $graph->as_graphml_file();
27$graphml_file =~ s/\n.*<!--.*-->\n//;
28
29_compare ($graph, $graphml_file, 'as_graphml and as_graphml_file are equal');
30
31my $graphml = $graph->as_graphml();
32like ($graphml, qr/<\?xml version="1.0" encoding="UTF-8"\?>/, 'as_graphml looks like xml');
33
34#############################################################################
35# some nodes and edges
36
37$graph->add_edge('Ursel','Viersen');
38
39$graphml = $graph->as_graphml();
40
41like ($graphml, qr/<node.*id="Ursel"/, 'as_graphml contains nodes');
42like ($graphml, qr/<node.*id="Viersen"/, 'as_graphml contains nodes');
43like ($graphml, qr/<edge.*source="Ursel"/, 'as_graphml contains edge');
44like ($graphml, qr/<edge.*target="Viersen"/, 'as_graphml contains edge');
45
46#############################################################################
47# some attributes:
48
49# node.foo { color: red; } [A] {class:foo;}-> { color: blue; } [B]
50$graph = Graph::Easy->new();
51my ($A,$B,$edge) = $graph->add_edge('A','B');
52
53$graph->set_attribute('node.foo','color','red');
54$edge->set_attribute('color','blue');
55$A->set_attribute('class','foo');
56
57my $result = <<EOT
58  <key id="d0" for="node" attr.name="color" attr.type="string">
59    <default>black</default>
60  </key>
61  <key id="d1" for="edge" attr.name="color" attr.type="string">
62    <default>black</default>
63  </key>
64
65  <graph id="G" edgedefault="directed">
66    <node id="A">
67      <data key="d0">red</data>
68    </node>
69    <node id="B">
70    </node>
71
72    <edge source="A" target="B">
73      <data key="d1">blue</data>
74    </edge>
75  </graph>
76</graphml>
77EOT
78;
79
80_compare($graph, $result, 'GraphML with attributes');
81
82#############################################################################
83# some attributes with no default valu with no default value:
84
85# Also test escaping for valid XML:
86
87$edge->set_attribute('label', 'train-station & <Überlingen "Süd">');
88
89$result = <<EOT2
90  <key id="d0" for="node" attr.name="color" attr.type="string">
91    <default>black</default>
92  </key>
93  <key id="d1" for="edge" attr.name="color" attr.type="string">
94    <default>black</default>
95  </key>
96  <key id="d2" for="edge" attr.name="label" attr.type="string"/>
97
98  <graph id="G" edgedefault="directed">
99    <node id="A">
100      <data key="d0">red</data>
101    </node>
102    <node id="B">
103    </node>
104
105    <edge source="A" target="B">
106      <data key="d1">blue</data>
107      <data key="d2">train-station &amp; &lt;Überlingen &quot;Süd&quot;&gt;</data>
108    </edge>
109  </graph>
110</graphml>
111EOT2
112;
113
114_compare($graph, $result, 'GraphML with attributes');
115
116#############################################################################
117# node names with things that need escaping:
118
119$graph->rename_node('A', '<&\'">');
120
121$result = <<EOT3
122  <key id="d0" for="node" attr.name="color" attr.type="string">
123    <default>black</default>
124  </key>
125  <key id="d1" for="edge" attr.name="color" attr.type="string">
126    <default>black</default>
127  </key>
128  <key id="d2" for="edge" attr.name="label" attr.type="string"/>
129
130  <graph id="G" edgedefault="directed">
131    <node id="&lt;&amp;&apos;&quot;&gt;">
132      <data key="d0">red</data>
133    </node>
134    <node id="B">
135    </node>
136
137    <edge source="&lt;&amp;&apos;&quot;&gt;" target="B">
138      <data key="d1">blue</data>
139      <data key="d2">train-station &amp; &lt;Überlingen &quot;Süd&quot;&gt;</data>
140    </edge>
141  </graph>
142</graphml>
143EOT3
144;
145
146_compare($graph, $result, 'GraphML with attributes');
147
148#############################################################################
149# double attributes
150
151$graph = Graph::Easy->new();
152($A,$B,$edge) = $graph->add_edge('A','B');
153my ($C,$D,$edge2) = $graph->add_edge('A','C');
154
155$edge->set_attribute('label','car');
156$edge2->set_attribute('label','train');
157
158$result = <<EOT4
159  <key id="d0" for="edge" attr.name="label" attr.type="string"/>
160
161  <graph id="G" edgedefault="directed">
162    <node id="A">
163    </node>
164    <node id="B">
165    </node>
166    <node id="C">
167    </node>
168
169    <edge source="A" target="B">
170      <data key="d0">car</data>
171    </edge>
172    <edge source="A" target="C">
173      <data key="d0">train</data>
174    </edge>
175  </graph>
176</graphml>
177EOT4
178;
179
180_compare($graph, $result, 'GraphML with attributes');
181
182#############################################################################
183# as_graphml() with groups (bug until v0.63):
184
185$graph = Graph::Easy->new();
186my $bonn  = Graph::Easy::Node->new('Bonn');
187my $cities = $graph->add_group('Cities"');
188$cities->add_nodes($bonn);
189
190$result = <<EOT5
191  <graph id="G" edgedefault="directed">
192    <graph id="Cities&quot;" edgedefault="directed">
193      <node id="Bonn">
194      </node>
195    </graph>
196  </graph>
197</graphml>
198EOT5
199;
200
201_compare($graph, $result, 'GraphML with group');
202
203# all tests done
204
205#############################################################################
206#############################################################################
207
208sub _compare
209  {
210  my ($graph, $result, $name) = @_;
211
212  my $graphml = $graph->as_graphml();
213  $graphml =~ s/\n.*<!--.*-->\n//;
214
215  $result = <<EOR
216<?xml version="1.0" encoding="UTF-8"?>
217<graphml xmlns="http://graphml.graphdrawing.org/xmlns"
218    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
219    xsi:schemaLocation="http://graphml.graphdrawing.org/xmlns
220     http://graphml.graphdrawing.org/xmlns/1.0/graphml.xsd">
221
222EOR
223  . $result unless $result =~ /<\?xml/;
224
225  if (!is ($graphml, $result, $name))
226    {
227    eval { require Test::Differences; };
228    if (defined $Test::Differences::VERSION)
229      {
230      Test::Differences::eq_or_diff ($result, $graphml);
231      }
232    }
233  }
234