Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix duplicated step definitions from the same step locations #633

Closed
wants to merge 3 commits into from
Closed
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
12 changes: 10 additions & 2 deletions core/src/main/java/cucumber/runtime/RuntimeGlue.java
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,18 @@ public RuntimeGlue(UndefinedStepsTracker tracker, LocalizedXStreams localizedXSt
@Override
public void addStepDefinition(StepDefinition stepDefinition) {
StepDefinition previous = stepDefinitionsByPattern.get(stepDefinition.getPattern());
if (previous != null) {
if (previous == null) {
stepDefinitionsByPattern.put(stepDefinition.getPattern(), stepDefinition);
} else if (!haveSameLocation(previous, stepDefinition)) {
throw new DuplicateStepDefinitionException(previous, stepDefinition);
}
stepDefinitionsByPattern.put(stepDefinition.getPattern(), stepDefinition);
}

private boolean haveSameLocation(StepDefinition previous, StepDefinition current) {
String previousLocation = previous.getLocation(true);
String currentLocation = current.getLocation(true);

return previousLocation.equals(currentLocation);
}

@Override
Expand Down
39 changes: 31 additions & 8 deletions core/src/test/java/cucumber/runtime/RuntimeGlueTest.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package cucumber.runtime;

import cucumber.runtime.xstream.LocalizedXStreams;
import org.junit.Before;
import org.junit.Test;

import static org.junit.Assert.assertEquals;
Expand All @@ -9,18 +10,21 @@
import static org.mockito.Mockito.when;

public class RuntimeGlueTest {

private RuntimeGlue glue;

@Before
public void setUpGlue() throws Exception {
glue = new RuntimeGlue(new UndefinedStepsTracker(),
new LocalizedXStreams(Thread.currentThread().getContextClassLoader()));
}

@Test
public void throws_duplicate_error_on_dupe_stepdefs() {
RuntimeGlue glue = new RuntimeGlue(new UndefinedStepsTracker(), new LocalizedXStreams(Thread.currentThread().getContextClassLoader()));

StepDefinition a = mock(StepDefinition.class);
when(a.getPattern()).thenReturn("hello");
when(a.getLocation(true)).thenReturn("foo.bf:10");
StepDefinition a = mockStepDefinition("hello", "foo.bf:10");
glue.addStepDefinition(a);

StepDefinition b = mock(StepDefinition.class);
when(b.getPattern()).thenReturn("hello");
when(b.getLocation(true)).thenReturn("bar.bf:90");
StepDefinition b = mockStepDefinition("hello", "bar.bf:90");
try {
glue.addStepDefinition(b);
fail("should have failed");
Expand All @@ -29,4 +33,23 @@ public void throws_duplicate_error_on_dupe_stepdefs() {
}
}

@Test
public void does_not_throw_duplicate_error_on_dupe_stepdefs_with_identical_locations() {
StepDefinition a = mockStepDefinition("hello", "foo.bf:10");
glue.addStepDefinition(a);

StepDefinition b = mockStepDefinition("hello", "foo.bf:10");
glue.addStepDefinition(b);

// It would be great to write an assertion here to match
// the exact count of step definition added in the glue
}

private StepDefinition mockStepDefinition(String pattern, String location) {
StepDefinition stepDefinition = mock(StepDefinition.class);
when(stepDefinition.getPattern()).thenReturn(pattern);
when(stepDefinition.getLocation(true)).thenReturn(location);
return stepDefinition;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,6 @@
import cucumber.runtime.io.ResourceLoader;
import cucumber.runtime.io.ResourceLoaderClassFinder;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;

/**
* Glue code for running Cucumber via TestNG.
Expand All @@ -32,11 +29,6 @@ public TestNGCucumberRunner(Class clazz) {
RuntimeOptionsFactory runtimeOptionsFactory = new RuntimeOptionsFactory(clazz, new Class[]{CucumberOptions.class});
RuntimeOptions runtimeOptions = runtimeOptionsFactory.create();

// remove duplicates from glue path.
List<String> uniqueGlue = new ArrayList<String>(new HashSet<String>(runtimeOptions.getGlue()));
runtimeOptions.getGlue().clear();
runtimeOptions.getGlue().addAll(uniqueGlue);

TestNgReporter reporter = new TestNgReporter(System.out);
runtimeOptions.getFormatters().add(reporter);
ClassFinder classFinder = new ResourceLoaderClassFinder(resourceLoader, classLoader);
Expand Down