tikhomirov@497: /* tikhomirov@497: * Copyright (c) 2012 TMate Software Ltd tikhomirov@497: * tikhomirov@497: * This program is free software; you can redistribute it and/or modify tikhomirov@497: * it under the terms of the GNU General Public License as published by tikhomirov@497: * the Free Software Foundation; version 2 of the License. tikhomirov@497: * tikhomirov@497: * This program is distributed in the hope that it will be useful, tikhomirov@497: * but WITHOUT ANY WARRANTY; without even the implied warranty of tikhomirov@497: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the tikhomirov@497: * GNU General Public License for more details. tikhomirov@497: * tikhomirov@497: * For information on how to redistribute this software under tikhomirov@497: * the terms of a license other than GNU General Public License tikhomirov@497: * contact TMate Software at support@hg4j.com tikhomirov@497: */ tikhomirov@497: package org.tmatesoft.hg.test; tikhomirov@497: tikhomirov@497: import java.io.ByteArrayInputStream; tikhomirov@497: import java.io.ByteArrayOutputStream; tikhomirov@497: import java.io.IOException; tikhomirov@497: tikhomirov@497: import org.junit.Assert; tikhomirov@497: import org.junit.Test; tikhomirov@497: import org.tmatesoft.hg.internal.ConfigFileParser; tikhomirov@497: tikhomirov@497: /** tikhomirov@497: * tikhomirov@497: * @author Artem Tikhomirov tikhomirov@497: * @author TMate Software Ltd. tikhomirov@497: */ tikhomirov@497: public class TestConfigFileParser { tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testParseOnly() throws IOException { tikhomirov@497: doTest("".getBytes(), new byte[0]); tikhomirov@497: // line comments tikhomirov@497: byte[] inp = " # line comment \n; and another one".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: // comments inside sections tikhomirov@497: inp = "[section1]\nkey1 = value\n # line comment\n[section2]\nkey2 = ;just presence\n".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: // empty value tikhomirov@497: inp = "[section1]\nkey1 = \n".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: // multiline values tikhomirov@497: inp = "[section1]\nkey1 = a,\n b,\n c\nkey2=\n xyz\n".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: // entry without EOL tikhomirov@497: inp = "[section1]\nkey1 = value".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: // empty section tikhomirov@497: inp = "[section1]\nkey1 = value\n[section2]\n".getBytes(); tikhomirov@497: doTest(inp, inp); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testLookup() throws IOException { tikhomirov@497: byte[] inp = "[section1]\nkey1 = a,\n b,\n c\nkey2=\n xyz\n\n[section2]\nkey3=\n".getBytes(); tikhomirov@497: doTest(inp, inp, new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: Assert.assertTrue(p.exists("section1", "key1")); tikhomirov@497: Assert.assertTrue(p.exists("section1", "key2")); tikhomirov@497: Assert.assertFalse(p.exists("section1", "key3")); tikhomirov@497: tikhomirov@497: Assert.assertTrue(p.exists("section2", "key3")); tikhomirov@497: Assert.assertFalse(p.exists("section2", "key1")); tikhomirov@497: Assert.assertFalse(p.exists("section2", "key2")); tikhomirov@497: } tikhomirov@497: }); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testAddChangeEntries() throws IOException { tikhomirov@497: byte[] inp = "\n; line comment1\n[sect-a]\nkey1 = value1\n\n[sect-b]\nkey2=value2\n".getBytes(); tikhomirov@497: byte[] exp = "\n; line comment1\n[sect-a]\nkey1 = value1\nkey3 = value3\n\n[sect-b]\nkey2=valueX\n".getBytes(); tikhomirov@497: doTest(inp, exp, new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: Assert.assertTrue(p.exists("sect-b", "key2")); tikhomirov@497: p.add("sect-a", "key3", "value3"); tikhomirov@497: p.change("sect-b", "key2", "valueX"); tikhomirov@497: } tikhomirov@497: }); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testAdditionTwoSectionsSameName() throws IOException { tikhomirov@497: byte[] inp = "[sect-a]\nkey1=value1\n\n[sect-b]\nkey2=\n\n[sect-a]\nkey3=value3\n".getBytes(); tikhomirov@497: byte[] exp = "[sect-a]\nkey1=value1\nkey4 = value4\n\n[sect-b]\nkey2=\n\n[sect-a]\nkey3=value3\n".getBytes(); tikhomirov@497: doTest(inp, exp, new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: p.add("sect-a", "key4", "value4"); tikhomirov@497: } tikhomirov@497: }); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testDeleteTwoSubsequentKeys() throws IOException{ tikhomirov@497: byte[] inp = "# line comment1\n\n[sect-a]\nkey1=value1\nkey2=value2\n#line comment2\nkey3=value3\n".getBytes(); tikhomirov@497: byte[] exp = "# line comment1\n\n[sect-a]\n\n\n#line comment2\nkey3=value3\n".getBytes(); tikhomirov@497: doTest(inp, exp, new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: p.delete("sect-a", "key1"); tikhomirov@497: p.delete("sect-a", "key2"); tikhomirov@497: } tikhomirov@497: }); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testDeleteLastKeyInSection() throws IOException { tikhomirov@497: String text1 = "[sect-a]\nkey0 = value 0\n%skey1=value1\n%s[sect-b]\nkey3=value3\n"; tikhomirov@497: String text2 = "[sect-a]\nkey0 = value 0\n%s\n%s[sect-b]\nkey3=value3\n"; tikhomirov@497: withTwoCommentsDeleteKey1(text1, text2); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testDeleteFirstKeyInSection() throws IOException { tikhomirov@497: String text1 = "[sect-a]\n%skey1=value1\n%skey2 = value 2\n[sect-b]\nkey3=value3\n"; tikhomirov@497: String text2 = "[sect-a]\n%s\n%skey2 = value 2\n[sect-b]\nkey3=value3\n"; tikhomirov@497: withTwoCommentsDeleteKey1(text1, text2); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@499: public void testDeleteOnlyKeyInSection() throws IOException { tikhomirov@497: String text1 = "[sect-a]\n%skey1=value1\n%s[sect-b]\nkey3=value3\n"; tikhomirov@497: String text2 = "[sect-a]\n%s\n%s[sect-b]\nkey3=value3\n"; tikhomirov@497: withTwoCommentsDeleteKey1(text1, text2); tikhomirov@497: } tikhomirov@497: tikhomirov@499: @Test tikhomirov@499: public void testAddNewSection() throws IOException { tikhomirov@499: byte[] inp = "[sect-a]\nkey1=value1\n".getBytes(); tikhomirov@499: byte[] exp = "[sect-a]\nkey1=value1\n\n[sect-b]\nkey2 = value2\n".getBytes(); tikhomirov@499: doTest(inp, exp, new Inspector() { tikhomirov@499: tikhomirov@499: public void visit(ConfigFileParser p) { tikhomirov@499: p.add("sect-b", "key2", "value2"); tikhomirov@499: } tikhomirov@499: }); tikhomirov@499: } tikhomirov@499: tikhomirov@497: private void withTwoCommentsDeleteKey1(String text1, String text2) throws IOException { tikhomirov@497: String comment = "# line comment\n"; tikhomirov@497: Inspector insp = new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: p.delete("sect-a", "key1"); tikhomirov@497: } tikhomirov@497: }; tikhomirov@497: tikhomirov@497: byte[] inp = String.format(text1, "", "").getBytes(); tikhomirov@497: byte[] exp = String.format(text2, "", "").getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: inp = String.format(text1, comment, "").getBytes(); tikhomirov@497: exp = String.format(text2, comment, "").getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: inp = String.format(text1, "", comment).getBytes(); tikhomirov@497: exp = String.format(text2, "", comment).getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: inp = String.format(text1, comment, comment).getBytes(); tikhomirov@497: exp = String.format(text2, comment, comment).getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: } tikhomirov@497: tikhomirov@497: @Test tikhomirov@497: public void testAddEntryToEmptySection() throws IOException { tikhomirov@497: String text1 = "[sect-a]\n%s[sect-b]\nkey3=value3\n"; tikhomirov@497: String text2 = "[sect-a]\n%skey1 = value1\n[sect-b]\nkey3=value3\n"; tikhomirov@497: String comment = "# line comment2\n"; tikhomirov@497: Inspector insp = new Inspector() { tikhomirov@497: tikhomirov@497: public void visit(ConfigFileParser p) { tikhomirov@497: p.add("sect-a", "key1", "value1"); tikhomirov@497: } tikhomirov@497: }; tikhomirov@497: tikhomirov@497: byte[] inp = String.format(text1, "").getBytes(); tikhomirov@497: byte[] exp = String.format(text2, "").getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: inp = String.format(text1, comment).getBytes(); tikhomirov@497: exp = String.format(text2, comment).getBytes(); tikhomirov@497: doTest(inp, exp, insp); tikhomirov@497: } tikhomirov@497: tikhomirov@497: tikhomirov@497: private void doTest(byte[] input, byte[] expected) throws IOException { tikhomirov@497: doTest(input, expected, null); tikhomirov@497: } tikhomirov@497: tikhomirov@497: private void doTest(byte[] input, byte[] expected, Inspector insp) throws IOException { tikhomirov@497: ConfigFileParser p = new ConfigFileParser(); tikhomirov@497: p.parse(new ByteArrayInputStream(input)); tikhomirov@497: if (insp != null) { tikhomirov@497: insp.visit(p); tikhomirov@497: } tikhomirov@497: ByteArrayOutputStream out = new ByteArrayOutputStream(input.length); tikhomirov@497: p.update(out); tikhomirov@497: byte[] result = out.toByteArray(); tikhomirov@497: Assert.assertArrayEquals(expected, result); tikhomirov@497: } tikhomirov@497: tikhomirov@497: interface Inspector { tikhomirov@497: void visit(ConfigFileParser p); tikhomirov@497: } tikhomirov@497: }