Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,7 @@ import quickfix.Group;</xsl:if>
</xsl:if>
</xsl:template>

<xsl:template mode="group-delimeter" match="group//component">
<xsl:template mode="group-delimeter" match="component">
<xsl:if test="position() = 1">
<xsl:variable name="name" select="@name"/>
<xsl:apply-templates select="/fix/components/component[@name=$name]/*[name(.)='field' or name(.)='group' or name(.)='component']"
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
package org.quickfixj.codegenerator;

import static org.junit.Assert.*;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Scanner;

import org.apache.maven.plugin.MojoExecutionException;
import org.junit.Before;
import org.junit.Test;
import org.apache.commons.io.FileUtils;

/**
* Test for nested component delimiter generation (issue #1084).
* Verifies that when a group's first element is a component whose first element
* is another component (nested > 1), the correct delimiter field number is used.
*/
public class NestedComponentDelimiterTest {

private File outputDirectory = new File("./target/test-output/nested-components");
private File dictDirectory = new File("./src/test/resources/org/quickfixj/codegenerator");
private File schemaDirectory = new File("./src/main/resources/org/quickfixj/codegenerator");
private String fieldPackage = "quickfix.field";
private String utcTimestampPrecision = null;
private boolean orderedFields = true;
private boolean decimal = true;
private MessageCodeGenerator generator;

@Before
public void setup() throws IOException {
if (outputDirectory.exists()) {
FileUtils.cleanDirectory(outputDirectory);
} else {
outputDirectory.mkdirs();
}
generator = new MessageCodeGenerator();
System.out.println("Successfully created an instance of the QuickFIX source generator");
}

@Test
public void testNestedComponentDelimiterGeneration() throws MojoExecutionException {
MessageCodeGenerator.Task task = new MessageCodeGenerator.Task();
System.out.println("Initialising code generator task for nested components test");

String packaging = "quickfix.test";
File dictFile = new File(dictDirectory, "NestedComponentsTest.xml");
generate(generator, task, dictFile, packaging, true);

// Check that NestedTwice component was generated
String nestedTwiceFilePath = outputDirectory.getAbsolutePath() +
"/quickfix/test/component/NestedTwice.java";
File nestedTwiceFile = new File(nestedTwiceFilePath);
assertTrue("NestedTwice.java should be generated", nestedTwiceFile.exists());

// Read the file and check for the correct delimiter
String content = readFileContent(nestedTwiceFile);

// The NoEntries group should have the correct delimiter (58 = Text field number)
// Expected: super(20001, 58, ORDER);
assertTrue("Generated code should contain 'super(20001, 58, ORDER);'",
content.contains("super(20001, 58, ORDER);"));

// Verify structural elements are present
assertTrue("Generated code should contain NoEntries class",
content.contains("public static class NoEntries extends Group"));

assertTrue("Generated code should contain ORDER array",
content.contains("private static final int[] ORDER"));
}

private void generate(MessageCodeGenerator generator, MessageCodeGenerator.Task task,
File dictfile, String packaging, boolean overwrite) throws MojoExecutionException {
if (dictfile != null && dictfile.exists()) {
task.setSpecification(dictfile);
} else {
throw new MojoExecutionException("File could not be found or was NULL!");
}

System.out.println("Processing " + dictfile);

task.setName(dictfile.getName());
task.setTransformDirectory(schemaDirectory);
task.setMessagePackage(packaging);
task.setOutputBaseDirectory(outputDirectory);
task.setFieldPackage(fieldPackage);
task.setUtcTimestampPrecision(utcTimestampPrecision);
task.setOverwrite(overwrite);
task.setOrderedFields(orderedFields);
task.setDecimalGenerated(decimal);
generator.generate(task);
}

private String readFileContent(File file) {
StringBuilder content = new StringBuilder();
try (Scanner scanner = new Scanner(file)) {
while (scanner.hasNextLine()) {
content.append(scanner.nextLine()).append("\n");
}
} catch (FileNotFoundException e) {
e.printStackTrace();
fail("Failed to read file: " + file.getAbsolutePath());
}
return content.toString();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
<?xml version="1.0" encoding="UTF-8"?>
<fix major="4" minor="4">
<header>
<field name="BeginString" required="Y"/>
<field name="BodyLength" required="Y"/>
<field name="MsgType" required="Y"/>
<field name="SenderCompID" required="Y"/>
<field name="TargetCompID" required="Y"/>
<field name="MsgSeqNum" required="Y"/>
<field name="SendingTime" required="Y"/>
</header>
<trailer>
<field name="CheckSum" required="Y"/>
</trailer>
<messages>
<message name="TestMessage" msgtype="TEST" msgcat="app">
<component name="NestedTwice" required="N"/>
</message>
</messages>
<components>
<component name="Level2">
<field name="Text" required="N"/>
</component>
<component name="Level1">
<component name="Level2" required="N"/>
</component>
<component name="NestedTwice">
<group name="NoEntries" required="N">
<component name="Level1" required="N"/>
</group>
</component>
</components>
<fields>
<field number="58" name="Text" type="STRING"/>
<field number="20001" name="NoEntries" type="NUMINGROUP"/>
</fields>
</fix>
Loading