package jmri.jmrit.display.logixng.configurexml; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertTrue; import static org.junit.jupiter.api.Assertions.fail; import java.beans.PropertyVetoException; import java.io.*; import java.nio.charset.StandardCharsets; import java.util.*; import jmri.*; import jmri.jmrit.display.logixng.ActionAudioIcon; import jmri.jmrit.display.logixng.ActionLayoutTurnout; import jmri.jmrit.display.logixng.ActionPositionable; import jmri.jmrit.display.logixng.ActionPositionableByClass; import jmri.jmrit.logixng.*; import jmri.jmrit.logixng.actions.IfThenElse; import jmri.jmrit.logixng.actions.DigitalMany; import jmri.jmrit.logixng.expressions.And; import jmri.jmrit.logixng.util.LogixNG_Thread; import jmri.util.*; import jmri.util.junit.annotations.DisabledIfHeadless; import org.apache.commons.lang3.mutable.MutableInt; import org.junit.jupiter.api.*; /** * Creates a LogixNG with all actions and expressions to test store and load. *

* It uses the Base.printTree(PrintWriter writer, String indent) method to * compare the LogixNGs before and after store and load. * * @author Daniel Bergqvist Copyright 2020 */ public class StoreAndLoadTest { @Test @DisabledIfHeadless public void testLogixNGs() throws PropertyVetoException, SocketAlreadyConnectedException, IOException, JmriException { LogixNG_Manager logixNG_Manager = InstanceManager.getDefault(LogixNG_Manager.class); ConditionalNG_Manager conditionalNGManager = InstanceManager.getDefault(ConditionalNG_Manager.class); DigitalActionManager digitalActionManager = InstanceManager.getDefault(DigitalActionManager.class); DigitalExpressionManager digitalExpressionManager = InstanceManager.getDefault(DigitalExpressionManager.class); LogixNG logixNG = logixNG_Manager.createLogixNG("A logixNG"); ConditionalNG conditionalNG = conditionalNGManager.createConditionalNG(logixNG, "A conditionalNG"); logixNG.setEnabled(false); conditionalNG.setEnabled(true); FemaleSocket femaleSocket = conditionalNG.getFemaleSocket(); IfThenElse ifThenElse = new IfThenElse(digitalActionManager.getAutoSystemName(), null); MaleSocket maleSocket = digitalActionManager.registerAction(ifThenElse); femaleSocket.connect(maleSocket); And and = new And(digitalExpressionManager.getAutoSystemName(), null); and.setComment("A comment"); maleSocket = digitalExpressionManager.registerExpression(and); ifThenElse.getChild(0).connect(maleSocket); /* ExpressionSlotUsage expressionSlotUsage = new ExpressionSlotUsage(digitalExpressionManager.getAutoSystemName(), null, null); maleSocket = digitalExpressionManager.registerExpression(expressionSlotUsage); and.getChild(0).connect(maleSocket); expressionSlotUsage = new ExpressionSlotUsage(digitalExpressionManager.getAutoSystemName(), null, memo1); expressionSlotUsage.setAdvanced(false); expressionSlotUsage.set_Has_HasNot(ExpressionSlotUsage.Has_HasNot.HasNot); expressionSlotUsage.setSimpleState(ExpressionSlotUsage.SimpleState.InUse); expressionSlotUsage.setCompare(ExpressionSlotUsage.Compare.Equal); expressionSlotUsage.setNumber(20); expressionSlotUsage.setPercentPieces(ExpressionSlotUsage.PercentPieces.Percent); expressionSlotUsage.setTotalSlots(30); maleSocket = digitalExpressionManager.registerExpression(expressionSlotUsage); and.getChild(1).connect(maleSocket); expressionSlotUsage = new ExpressionSlotUsage(digitalExpressionManager.getAutoSystemName(), null, memo2); expressionSlotUsage.setComment("A comment"); expressionSlotUsage.setAdvanced(false); expressionSlotUsage.set_Has_HasNot(ExpressionSlotUsage.Has_HasNot.Has); expressionSlotUsage.setSimpleState(ExpressionSlotUsage.SimpleState.Free); expressionSlotUsage.setAdvancedStates(states); expressionSlotUsage.setCompare(ExpressionSlotUsage.Compare.GreaterThan); expressionSlotUsage.setNumber(11); expressionSlotUsage.setPercentPieces(ExpressionSlotUsage.PercentPieces.Pieces); expressionSlotUsage.setTotalSlots(0); maleSocket = digitalExpressionManager.registerExpression(expressionSlotUsage); and.getChild(2).connect(maleSocket); */ DigitalMany digitalMany = new DigitalMany(digitalActionManager.getAutoSystemName(), null); digitalMany.setComment("A comment"); maleSocket = digitalActionManager.registerAction(digitalMany); ifThenElse.getChild(1).connect(maleSocket); int index = 0; ActionAudioIcon actionAudioIcon = new ActionAudioIcon(digitalActionManager.getAutoSystemName(), null); actionAudioIcon.setComment("A comment"); maleSocket = digitalActionManager.registerAction(actionAudioIcon); digitalMany.getChild(index++).connect(maleSocket); actionAudioIcon = new ActionAudioIcon(digitalActionManager.getAutoSystemName(), null); actionAudioIcon.setComment("A comment"); actionAudioIcon.setOperation(ActionAudioIcon.Operation.Play); maleSocket = digitalActionManager.registerAction(actionAudioIcon); digitalMany.getChild(index++).connect(maleSocket); actionAudioIcon = new ActionAudioIcon(digitalActionManager.getAutoSystemName(), null); actionAudioIcon.setComment("A comment"); actionAudioIcon.setOperation(ActionAudioIcon.Operation.Stop); maleSocket = digitalActionManager.registerAction(actionAudioIcon); digitalMany.getChild(index++).connect(maleSocket); ActionLayoutTurnout actionLayoutTurnout = new ActionLayoutTurnout(digitalActionManager.getAutoSystemName(), null); actionLayoutTurnout.setComment("A comment"); maleSocket = digitalActionManager.registerAction(actionLayoutTurnout); digitalMany.getChild(index++).connect(maleSocket); ActionPositionable actionPositionable = new ActionPositionable(digitalActionManager.getAutoSystemName(), null); actionPositionable.setComment("A comment"); maleSocket = digitalActionManager.registerAction(actionPositionable); digitalMany.getChild(index++).connect(maleSocket); ActionPositionableByClass actionPositionableByClass = new ActionPositionableByClass(digitalActionManager.getAutoSystemName(), null); actionPositionableByClass.setComment("A comment"); maleSocket = digitalActionManager.registerAction(actionPositionableByClass); digitalMany.getChild(index++).connect(maleSocket); /* if (1==1) { final String treeIndent = " "; StringWriter stringWriter = new StringWriter(); PrintWriter printWriter = new PrintWriter(stringWriter); logixNG_Manager.printTree(Locale.ENGLISH, printWriter, treeIndent); System.out.println("--------------------------------------------"); System.out.println("The current tree:"); System.out.println("XXX"+stringWriter.toString()+"XXX"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); System.out.println("--------------------------------------------"); log.error("--------------------------------------------"); log.error("The current tree:"); log.error("XXX"+stringWriter.toString()+"XXX"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); log.error("--------------------------------------------"); // return; } */ // Store panels jmri.ConfigureManager cm = InstanceManager.getNullableDefault(jmri.ConfigureManager.class); if (cm == null) { log.error("Unable to get default configure manager"); } else { FileUtil.createDirectory(FileUtil.getUserFilesPath() + "temp"); File firstFile = new File(FileUtil.getUserFilesPath() + "temp/" + "LogixNG_temp.xml"); File secondFile = new File(FileUtil.getUserFilesPath() + "temp/" + "LogixNG.xml"); log.info("Temporary first file: {}", firstFile.getAbsoluteFile()); log.info("Temporary second file: {}", secondFile.getAbsoluteFile()); final String treeIndent = " "; StringWriter stringWriter = new StringWriter(); PrintWriter printWriter = new PrintWriter(stringWriter); logixNG_Manager.printTree(Locale.ENGLISH, printWriter, treeIndent, new MutableInt(0)); final String originalTree = stringWriter.toString(); boolean results = cm.storeUser(firstFile); log.debug(results ? "store was successful" : "store failed"); assertTrue( results, "Failed to store panel"); // Add the header comment to the xml file addHeader(firstFile, secondFile); //********************************** // Delete all the LogixNGs, ConditionalNGs, and so on before reading the file. //********************************** java.util.Set logixNG_Set = new java.util.HashSet<>(logixNG_Manager.getNamedBeanSet()); for (LogixNG aLogixNG : logixNG_Set) { logixNG_Manager.deleteLogixNG(aLogixNG); } java.util.Set conditionalNGSet = new java.util.HashSet<>(conditionalNGManager.getNamedBeanSet()); for (ConditionalNG aConditionalNG : conditionalNGSet) { conditionalNGManager.deleteConditionalNG(aConditionalNG); } java.util.Set digitalActionSet = new java.util.HashSet<>(digitalActionManager.getNamedBeanSet()); for (MaleDigitalActionSocket aDigitalActionSocket : digitalActionSet) { digitalActionManager.deleteDigitalAction(aDigitalActionSocket); } java.util.Set digitalExpressionSet = new java.util.HashSet<>(digitalExpressionManager.getNamedBeanSet()); for (MaleDigitalExpressionSocket aDigitalExpression : digitalExpressionSet) { digitalExpressionManager.deleteDigitalExpression(aDigitalExpression); } assertEquals(0, logixNG_Manager.getNamedBeanSet().size()); assertEquals(0, conditionalNGManager.getNamedBeanSet().size()); assertEquals(0, digitalActionManager.getNamedBeanSet().size()); assertEquals(0, digitalExpressionManager.getNamedBeanSet().size()); LogixNG_Thread.stopAllLogixNGThreads(); LogixNG_Thread.assertLogixNGThreadNotRunning(); //********************************** // Try to load file //********************************** java.util.Set conditionalNG_Set = new java.util.HashSet<>(conditionalNGManager.getNamedBeanSet()); for (ConditionalNG aConditionalNG : conditionalNG_Set) { conditionalNGManager.deleteConditionalNG(aConditionalNG); } java.util.SortedSet set3 = digitalActionManager.getNamedBeanSet(); List l = new ArrayList<>(set3); for (MaleSocket x3 : l) { digitalActionManager.deleteBean((MaleDigitalActionSocket)x3, "DoDelete"); } java.util.SortedSet set4 = digitalExpressionManager.getNamedBeanSet(); l = new ArrayList<>(set4); for (MaleSocket x4 : l) { digitalExpressionManager.deleteBean((MaleDigitalExpressionSocket)x4, "DoDelete"); } results = cm.load(secondFile); log.debug(results ? "load was successful" : "store failed"); if (results) { logixNG_Manager.setupAllLogixNGs(); stringWriter = new StringWriter(); printWriter = new PrintWriter(stringWriter); logixNG_Manager.printTree(Locale.ENGLISH, printWriter, treeIndent, new MutableInt(0)); if (!originalTree.equals(stringWriter.toString())) { log.error("--------------------------------------------"); log.error("Old tree:"); log.error("XXX"+originalTree+"XXX"); log.error("--------------------------------------------"); log.error("New tree:"); log.error("XXX"+stringWriter.toString()+"XXX"); log.error("--------------------------------------------"); /* System.out.println("--------------------------------------------"); System.out.println("Old tree:"); System.out.println("XXX"+originalTree+"XXX"); System.out.println("--------------------------------------------"); System.out.println("New tree:"); System.out.println("XXX"+stringWriter.toString()+"XXX"); System.out.println("--------------------------------------------"); */ // log.error(conditionalNGManager.getBySystemName(originalTree).getChild(0).getConnectedSocket().getSystemName()); fail("tree has changed"); } } else { fail("Failed to load panel"); } } } private void addHeader(File inFile, File outFile) throws FileNotFoundException, IOException { try (BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream(inFile), StandardCharsets.UTF_8)); PrintWriter writer = new PrintWriter(new BufferedWriter(new OutputStreamWriter(new FileOutputStream(outFile), StandardCharsets.UTF_8)))) { String line = reader.readLine(); writer.println(line); writer.println(""); while ((line = reader.readLine()) != null) { writer.println(line); } } } @BeforeEach public void setUp() { JUnitUtil.setUp(); JUnitUtil.resetInstanceManager(); JUnitUtil.resetProfileManager(); JUnitUtil.initConfigureManager(); JUnitUtil.initInternalTurnoutManager(); JUnitUtil.initInternalLightManager(); JUnitUtil.initInternalSensorManager(); JUnitUtil.initInternalSignalHeadManager(); JUnitUtil.initDefaultSignalMastManager(); // JUnitUtil.initSignalMastLogicManager(); JUnitUtil.initOBlockManager(); JUnitUtil.initWarrantManager(); // JUnitUtil.initLogixNGManager(); } @AfterEach public void tearDown() { // JUnitAppender.clearBacklog(); // REMOVE THIS!!! jmri.jmrit.logixng.util.LogixNG_Thread.stopAllLogixNGThreads(); JUnitUtil.deregisterBlockManagerShutdownTask(); JUnitUtil.tearDown(); } private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(StoreAndLoadTest.class); }