Change all copyright headers to include 2012.
[Sone.git] / src / test / java / net / pterodactylus / sone / text / SoneTextParserTest.java
1 /*
2  * Sone - SoneTextParserTest.java - Copyright © 2011–2012 David Roden
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or
7  * (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
16  */
17
18 package net.pterodactylus.sone.text;
19
20 import java.io.IOException;
21 import java.io.StringReader;
22
23 import junit.framework.TestCase;
24 import net.pterodactylus.sone.core.SoneProvider;
25 import net.pterodactylus.sone.data.Sone;
26
27 /**
28  * JUnit test case for {@link SoneTextParser}.
29  *
30  * @author <a href="mailto:bombe@pterodactylus.net">David ‘Bombe’ Roden</a>
31  */
32 public class SoneTextParserTest extends TestCase {
33
34         //
35         // ACTIONS
36         //
37
38         /**
39          * Tests basic plain-text operation of the parser.
40          *
41          * @throws IOException
42          *             if an I/O error occurs
43          */
44         public void testPlainText() throws IOException {
45                 SoneTextParser soneTextParser = new SoneTextParser(null, null);
46                 Iterable<Part> parts;
47
48                 /* check basic operation. */
49                 parts = soneTextParser.parse(null, new StringReader("Test."));
50                 assertNotNull("Parts", parts);
51                 assertEquals("Part Text", "Test.", convertText(parts, PlainTextPart.class));
52
53                 /* check empty lines at start and end. */
54                 parts = soneTextParser.parse(null, new StringReader("\nTest.\n\n"));
55                 assertNotNull("Parts", parts);
56                 assertEquals("Part Text", "Test.", convertText(parts, PlainTextPart.class));
57
58                 /* check duplicate empty lines in the text. */
59                 parts = soneTextParser.parse(null, new StringReader("\nTest.\n\n\nTest."));
60                 assertNotNull("Parts", parts);
61                 assertEquals("Part Text", "Test.\n\nTest.", convertText(parts, PlainTextPart.class));
62         }
63
64         /**
65          * Tests parsing of KSK links.
66          *
67          * @throws IOException
68          *             if an I/O error occurs
69          */
70         public void testKSKLinks() throws IOException {
71                 SoneTextParser soneTextParser = new SoneTextParser(null, null);
72                 Iterable<Part> parts;
73
74                 /* check basic links. */
75                 parts = soneTextParser.parse(null, new StringReader("KSK@gpl.txt"));
76                 assertNotNull("Parts", parts);
77                 assertEquals("Part Text", "[KSK@gpl.txt|gpl.txt|gpl.txt]", convertText(parts, FreenetLinkPart.class));
78
79                 /* check embedded links. */
80                 parts = soneTextParser.parse(null, new StringReader("Link is KSK@gpl.txt\u200b."));
81                 assertNotNull("Parts", parts);
82                 assertEquals("Part Text", "Link is [KSK@gpl.txt|gpl.txt|gpl.txt]\u200b.", convertText(parts, PlainTextPart.class, FreenetLinkPart.class));
83
84                 /* check embedded links and line breaks. */
85                 parts = soneTextParser.parse(null, new StringReader("Link is KSK@gpl.txt\nKSK@test.dat\n"));
86                 assertNotNull("Parts", parts);
87                 assertEquals("Part Text", "Link is [KSK@gpl.txt|gpl.txt|gpl.txt]\n[KSK@test.dat|test.dat|test.dat]", convertText(parts, PlainTextPart.class, FreenetLinkPart.class));
88         }
89
90         /**
91          * Test case for a bug that was discovered in 0.6.7.
92          *
93          * @throws IOException
94          *             if an I/O error occurs
95          */
96         @SuppressWarnings("synthetic-access")
97         public void testEmptyLinesAndSoneLinks() throws IOException {
98                 SoneTextParser soneTextParser = new SoneTextParser(new TestSoneProvider(), null);
99                 Iterable<Part> parts;
100
101                 /* check basic links. */
102                 parts = soneTextParser.parse(null, new StringReader("Some text.\n\nLink to sone://DAxKQzS48mtaQc7sUVHIgx3fnWZPQBz0EueBreUVWrU and stuff."));
103                 assertNotNull("Parts", parts);
104                 assertEquals("Part Text", "Some text.\n\nLink to [Sone|DAxKQzS48mtaQc7sUVHIgx3fnWZPQBz0EueBreUVWrU] and stuff.", convertText(parts, PlainTextPart.class, SonePart.class));
105         }
106
107         //
108         // PRIVATE METHODS
109         //
110
111         /**
112          * Converts all given {@link Part}s into a string, validating that the
113          * part’s classes match only the expected classes.
114          *
115          * @param parts
116          *            The parts to convert to text
117          * @param validClasses
118          *            The valid classes; if no classes are given, all classes are
119          *            valid
120          * @return The converted text
121          */
122         private String convertText(Iterable<Part> parts, Class<?>... validClasses) {
123                 StringBuilder text = new StringBuilder();
124                 for (Part part : parts) {
125                         assertNotNull("Part", part);
126                         boolean classValid = validClasses.length == 0;
127                         for (Class<?> validClass : validClasses) {
128                                 if (validClass.isAssignableFrom(part.getClass())) {
129                                         classValid = true;
130                                         break;
131                                 }
132                         }
133                         if (!classValid) {
134                                 assertEquals("Part’s Class", null, part.getClass());
135                         }
136                         if (part instanceof PlainTextPart) {
137                                 text.append(((PlainTextPart) part).getText());
138                         } else if (part instanceof FreenetLinkPart) {
139                                 FreenetLinkPart freenetLinkPart = (FreenetLinkPart) part;
140                                 text.append('[').append(freenetLinkPart.getLink()).append('|').append(freenetLinkPart.isTrusted() ? "trusted|" : "").append(freenetLinkPart.getTitle()).append('|').append(freenetLinkPart.getText()).append(']');
141                         } else if (part instanceof LinkPart) {
142                                 LinkPart linkPart = (LinkPart) part;
143                                 text.append('[').append(linkPart.getLink()).append('|').append(linkPart.getTitle()).append('|').append(linkPart.getText()).append(']');
144                         } else if (part instanceof SonePart) {
145                                 SonePart sonePart = (SonePart) part;
146                                 text.append("[Sone|").append(sonePart.getSone().getId()).append(']');
147                         }
148                 }
149                 return text.toString();
150         }
151
152         /**
153          * Mock Sone provider.
154          *
155          * @author <a href="mailto:bombe@pterodactylus.net">David ‘Bombe’ Roden</a>
156          */
157         private static class TestSoneProvider implements SoneProvider {
158
159                 /**
160                  * {@inheritDoc}
161                  */
162                 @Override
163                 public Sone getSone(final String soneId, boolean create) {
164                         return new Sone(soneId) {
165
166                                 /**
167                                  * {@inheritDoc}
168                                  */
169                                 @Override
170                                 public String getName() {
171                                         return soneId;
172                                 }
173                         };
174                 }
175
176         }
177
178 }