Skip to content

Commit 4c49307

Browse files
authored
[svg2xml] fix destination path of generated files (#12)
Do not lowercase the generation output path. This was an issue on OS where path is case-sensitive (Linux, macOS). Several tests have been added to verify that the generation works on all OS.
1 parent 298728b commit 4c49307

15 files changed

Lines changed: 198 additions & 24 deletions

File tree

pom.xml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,11 @@
1818
<artifactId>jgraphx</artifactId>
1919
<version>4.1.0</version>
2020
</dependency>
21+
<dependency>
22+
<groupId>commons-io</groupId>
23+
<artifactId>commons-io</artifactId>
24+
<version>2.7</version>
25+
</dependency>
2126
<dependency>
2227
<groupId>org.junit.jupiter</groupId>
2328
<artifactId>junit-jupiter</artifactId>

src/main/java/com/mxgraph/svg2xml/Svg2Xml.java

Lines changed: 31 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@
3636
import javax.xml.transform.dom.DOMSource;
3737
import javax.xml.transform.stream.StreamResult;
3838

39+
import org.apache.commons.io.FileUtils;
3940
import org.w3c.dom.Document;
4041
import org.w3c.dom.Element;
4142
import org.w3c.dom.NamedNodeMap;
@@ -159,6 +160,26 @@ public void convertToXml(File[] sourceFiles, File destPath) {
159160
// {
160161
// sourceFolder = gui.sourceFileListComponent.getSelectedFiles()[0].getParent();
161162
// }
163+
// Basic implementation to mimic upstream/master
164+
// only used to compute the stencil groupName
165+
File rootSourceFolder = null;
166+
for (File sourceFile : sourceFiles) {
167+
File parent = sourceFile.getParentFile().getParentFile();
168+
if (rootSourceFolder == null) {
169+
rootSourceFolder = parent;
170+
continue;
171+
}
172+
173+
try {
174+
if (FileUtils.directoryContains(parent, rootSourceFolder)) {
175+
rootSourceFolder = parent;
176+
}
177+
} catch (IOException e) {
178+
// TODO error management
179+
e.printStackTrace();
180+
}
181+
}
182+
sourceFolder = rootSourceFolder.getAbsolutePath();
162183
// =============================================================================================================
163184
// END OF "NOTE"
164185
// =============================================================================================================
@@ -652,24 +673,24 @@ else if (aspectRatio.toLowerCase().equals("variable"))
652673

653674
try
654675
{
655-
String currentDestPath = destPath.getAbsolutePath() + File.separator + lastGroupName.replace(".", File.separator) + ".xml";
676+
// TODO fail if unable to mkdirs (or use commons-io)
677+
destPath.mkdirs();
656678

657-
currentDestPath = currentDestPath.toLowerCase();
658-
currentDestPath = currentDestPath.replaceAll("\\s", "_");
659-
File myDestFile = new File(currentDestPath);
660-
System.out.println("Prepare writing to " + myDestFile);
679+
String fileName = sourceFiles[i].getName();
680+
fileName = fileName.substring(0, fileName.lastIndexOf('.')) + ".xml";
681+
File destFile = new File(destPath, fileName);
682+
System.out.println("Prepare writing to " + destFile);
661683

662-
File myDestRoot = new File(myDestFile.getParent());
663-
myDestRoot.mkdirs();
664-
FileWriter fileWriter = new FileWriter(myDestFile);
684+
// TODO try-with-resource to improve resources management
685+
FileWriter fileWriter = new FileWriter(destFile);
665686
BufferedWriter writer = new BufferedWriter(fileWriter);
666687
writer.write(groupXml);
667688
writer.close();
668689
System.out.println("File written");
669690

670-
if (!destPaths.contains(myDestRoot))
691+
if (!destPaths.contains(destPath))
671692
{
672-
destPaths.add(myDestRoot);
693+
destPaths.add(destPath);
673694
}
674695

675696
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
package com.mxgraph.utils;
2+
3+
import java.io.File;
4+
import java.io.IOException;
5+
6+
import static java.nio.charset.StandardCharsets.UTF_8;
7+
import static java.nio.file.Files.lines;
8+
import static java.util.stream.Collectors.joining;
9+
10+
public class FileUtils {
11+
12+
public static final String EOL = System.lineSeparator();
13+
14+
// when switching to JDK11+, use Files#readString instead
15+
public static String fileContent(File file) {
16+
try {
17+
return lines(file.toPath(), UTF_8).collect(joining(EOL));
18+
} catch (IOException e) {
19+
throw new RuntimeException("Unable to read the content of " + file, e);
20+
}
21+
}
22+
23+
}

src/main/java/com/mxgraph/xml2js/Xml2Js.java

Lines changed: 2 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,12 @@
99
import javax.xml.parsers.DocumentBuilder;
1010
import javax.xml.parsers.DocumentBuilderFactory;
1111
import java.io.File;
12-
import java.io.IOException;
1312
import java.io.StringReader;
14-
import java.nio.file.Files;
1513
import java.util.ArrayList;
1614
import java.util.List;
1715

16+
import static com.mxgraph.utils.FileUtils.EOL;
17+
import static com.mxgraph.utils.FileUtils.fileContent;
1818
import static java.lang.String.format;
1919

2020
public class Xml2Js {
@@ -53,18 +53,6 @@ public String parse(File source) {
5353
return code;
5454
}
5555

56-
public static final String EOL = System.getProperty("line.separator");
57-
58-
private static String fileContent(File file) {
59-
// TODO java 11 use readString
60-
try {
61-
List<String> strings = Files.readAllLines(file.toPath());
62-
return String.join(EOL, strings);
63-
} catch (IOException e) {
64-
throw new RuntimeException("Unable to read the content of " + file, e);
65-
}
66-
}
67-
6856
private String parse(String shapeStencilXml) {
6957
List<String> lines = parseCodeLines(shapeStencilXml);
7058
return String.join(EOL, lines);
Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,97 @@
1+
package com.mxgraph.svg2xml;
2+
3+
import static com.mxgraph.utils.FileUtils.EOL;
4+
import static com.mxgraph.utils.FileUtils.fileContent;
5+
import static org.assertj.core.api.Assertions.assertThat;
6+
7+
import org.junit.jupiter.api.Test;
8+
import java.io.File;
9+
import java.util.Arrays;
10+
11+
class Svg2XmlTest {
12+
13+
@Test
14+
void convertToXml_single_file() {
15+
Svg2Xml svg2Xml = new Svg2Xml();
16+
17+
File destPath = destinationFolder("Simple-Single file");
18+
svg2Xml.convertToXml(svgSourceFiles("simple-01/circle-green.svg"), destPath);
19+
20+
File expectedGeneratedFile = new File(destPath, "circle-green.xml");
21+
assertThat(expectedGeneratedFile).isFile();
22+
String fileContent = fileContent(expectedGeneratedFile);
23+
assertThat(fileContent).startsWith("<shapes name=\"mxgraph.simple-01\">");
24+
assertThat(fileContent).contains(
25+
"<fillcolor color=\"green\"/>",
26+
"<ellipse h=\"200\" w=\"200\" x=\"0\" y=\"0\"/>"
27+
);
28+
}
29+
30+
@Test
31+
void convertToXml_two_files_from_the_same_folder() {
32+
Svg2Xml svg2Xml = new Svg2Xml();
33+
34+
File destPath = destinationFolder("Simple-Two files");
35+
svg2Xml.convertToXml(svgSourceFiles("simple-01/circle-green.svg", "simple-01/rectangle-blue.svg"), destPath);
36+
37+
File expectedGeneratedFile = new File(destPath, "rectangle-blue.xml"); // use base name of the latest svg file in the source folder
38+
assertThat(expectedGeneratedFile).isFile();
39+
String fileContent = fileContent(expectedGeneratedFile);
40+
assertThat(fileContent).startsWith("<shapes name=\"mxgraph.simple-01\">");
41+
assertThat(fileContent).contains(
42+
// 1st shape
43+
"<shape aspect=\"variable\" h=\"200\" name=\"circle-green\"",
44+
// 2nde shape
45+
"<shape aspect=\"variable\" h=\"100\" name=\"rectangle-blue\""
46+
);
47+
}
48+
49+
@Test
50+
void convertToXml_files_from_two_folders_without_subfolders_files_given_ordered_by_folders() {
51+
Svg2Xml svg2Xml = new Svg2Xml();
52+
53+
File destPath = destinationFolder("files from 2 folders - no subfolders");
54+
// in the current implementation, the files are supposed to be passed ordered by folder
55+
svg2Xml.convertToXml(svgSourceFiles("simple-01/circle-green.svg", "simple-01/rectangle-blue.svg", "simple-02/path-blue.svg"), destPath);
56+
57+
58+
// File generated from source files in 'simple-01'
59+
File expected1stGeneratedFile = new File(destPath, "rectangle-blue.xml");
60+
assertThat(expected1stGeneratedFile).isFile();
61+
String contentOfFirstFile = fileContent(expected1stGeneratedFile);
62+
assertThat(contentOfFirstFile).startsWith("<shapes name=\"mxgraph.simple-01\">");
63+
64+
// File generated from source files in 'simple-02'
65+
File expected2ndGeneratedFile = new File(destPath, "path-blue.xml");
66+
assertThat(expected2ndGeneratedFile).isFile();
67+
String contentOf2ndFile = fileContent(expected2ndGeneratedFile);
68+
assertThat(contentOf2ndFile).startsWith("<shapes name=\"mxgraph.simple-02\">");
69+
assertThat(contentOf2ndFile).describedAs("Content of the 2nd generated file").contains(
70+
"<quad x1=\"20\" x2=\"30\" y1=\"0\" y2=\"25\"/>",
71+
"<quad x1=\"40\" x2=\"70\" y1=\"50\" y2=\"25\"/>"
72+
);
73+
}
74+
75+
// =================================================================================================================
76+
// UTILS
77+
// =================================================================================================================
78+
79+
private static void assertFirstLine(String fileContent, String expectedStart, String expectedEnd) {
80+
String firstLine = fileContent.substring(0, fileContent.indexOf(EOL));
81+
assertThat(firstLine).describedAs("1st line of the generated file")
82+
.startsWith(expectedStart)
83+
.endsWith(expectedEnd);
84+
}
85+
86+
private static File[] svgSourceFiles(String... fileNames) {
87+
File parent = new File(System.getProperty("user.dir"), "src/test/resources/svg"); // ensure we pass absolute path
88+
return Arrays.stream(fileNames)
89+
.map(fileName -> new File(parent, fileName))
90+
.toArray(File[]::new);
91+
}
92+
93+
private static File destinationFolder(String folderName) {
94+
return new File("target/test/output/", folderName);
95+
}
96+
97+
}
Lines changed: 3 additions & 0 deletions
Loading
Lines changed: 3 additions & 0 deletions
Loading
Lines changed: 4 additions & 0 deletions
Loading
Lines changed: 4 additions & 0 deletions
Loading
Lines changed: 5 additions & 0 deletions
Loading

0 commit comments

Comments
 (0)