diff --git a/pom.xml b/pom.xml index 518f0589..e9da92c5 100644 --- a/pom.xml +++ b/pom.xml @@ -10,7 +10,7 @@ org.jenkins-ci.plugins plugin - 1.599 + 1.608 @@ -65,8 +65,6 @@ redis.clients jedis 2.6.0 - jar - compile @@ -88,8 +86,7 @@ org.mockito mockito-core - 2.1.0 - jar + 2.10.0 test @@ -127,6 +124,18 @@ structs 1.2 + + org.powermock + powermock-api-mockito2 + 2.0.0-beta.5 + test + + + org.powermock + powermock-module-junit4 + 2.0.0-beta.5 + test + diff --git a/src/main/java/jenkins/plugins/logstash/persistence/AbstractLogstashIndexerDao.java b/src/main/java/jenkins/plugins/logstash/persistence/AbstractLogstashIndexerDao.java index 25bd93c6..c17b61ce 100644 --- a/src/main/java/jenkins/plugins/logstash/persistence/AbstractLogstashIndexerDao.java +++ b/src/main/java/jenkins/plugins/logstash/persistence/AbstractLogstashIndexerDao.java @@ -37,14 +37,14 @@ * @author Rusty Gerard * @since 1.0.0 */ -abstract class AbstractLogstashIndexerDao implements LogstashIndexerDao { +public abstract class AbstractLogstashIndexerDao implements LogstashIndexerDao { protected final String host; protected final int port; protected final String key; protected final String username; protected final String password; - AbstractLogstashIndexerDao(String host, int port, String key, String username, String password) { + public AbstractLogstashIndexerDao(String host, int port, String key, String username, String password) { this.host = host; this.port = port; this.key = key; diff --git a/src/main/java/jenkins/plugins/logstash/persistence/BuildData.java b/src/main/java/jenkins/plugins/logstash/persistence/BuildData.java index abb8a5be..edb40760 100644 --- a/src/main/java/jenkins/plugins/logstash/persistence/BuildData.java +++ b/src/main/java/jenkins/plugins/logstash/persistence/BuildData.java @@ -138,7 +138,7 @@ public TestData(Action action) { public BuildData(AbstractBuild build, Date currentTime, TaskListener listener) { initData(build, currentTime); - Node node = build.getBuiltOn(); + Node node = build.getExecutor().getOwner().getNode(); if (node == null) { buildHost = "master"; buildLabel = "master"; @@ -186,11 +186,13 @@ public BuildData(AbstractBuild build, Date currentTime, TaskListener liste public BuildData(Run build, Date currentTime, TaskListener listener) { initData(build, currentTime); - Executor executor = build.getExecutor(); - if (executor == null) { + Node node = build.getExecutor().getOwner().getNode(); + if (node == null) { buildHost = "master"; + buildLabel = "master"; } else { - buildHost = StringUtils.isBlank(executor.getDisplayName()) ? "master" : executor.getDisplayName(); + buildHost = StringUtils.isBlank(node.getDisplayName()) ? "master" : node.getDisplayName(); + buildLabel = StringUtils.isBlank(node.getLabelString()) ? "master" : node.getLabelString(); } rootProjectName = projectName; diff --git a/src/test/java/jenkins/plugins/logstash/LogstashIntegrationTest.java b/src/test/java/jenkins/plugins/logstash/LogstashIntegrationTest.java new file mode 100644 index 00000000..36827135 --- /dev/null +++ b/src/test/java/jenkins/plugins/logstash/LogstashIntegrationTest.java @@ -0,0 +1,163 @@ +package jenkins.plugins.logstash; + +import static org.hamcrest.Matchers.equalTo; +import static org.hamcrest.Matchers.is; +import static org.junit.Assert.assertThat; +import static org.powermock.api.mockito.PowerMockito.when; + +import java.io.IOException; +import java.util.ArrayList; +import java.util.List; + +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.jvnet.hudson.test.JenkinsRule; +import org.powermock.api.mockito.PowerMockito; +import org.powermock.core.classloader.annotations.PowerMockIgnore; +import org.powermock.core.classloader.annotations.PrepareForTest; +import org.powermock.modules.junit4.PowerMockRunner; + +import hudson.model.FreeStyleBuild; +import hudson.model.FreeStyleProject; +import hudson.model.Result; +import hudson.model.Slave; +import hudson.model.queue.QueueTaskFuture; +import jenkins.plugins.logstash.persistence.AbstractLogstashIndexerDao; +import jenkins.plugins.logstash.persistence.IndexerDaoFactory; +import jenkins.plugins.logstash.persistence.LogstashIndexerDao.IndexerType; +import net.sf.json.JSONArray; +import net.sf.json.JSONObject; + +@RunWith(PowerMockRunner.class) +@PowerMockIgnore({"javax.crypto.*"}) +@PrepareForTest(IndexerDaoFactory.class) +public class LogstashIntegrationTest +{ + @Rule + public JenkinsRule jenkins = new JenkinsRule(); + + private Slave slave; + + private FreeStyleProject project; + + private MemoryDao memoryDao; + + @Before + public void setup() throws Exception + { + PowerMockito.mockStatic(IndexerDaoFactory.class); + LogstashInstallation.Descriptor descriptor = LogstashInstallation.getLogstashDescriptor(); + descriptor.type = IndexerType.SYSLOG; + descriptor.host = "localhost"; + descriptor.port = 1; + descriptor.username = "username"; + descriptor.password = "password"; + descriptor.key = "key"; + + memoryDao = new MemoryDao(); + when(IndexerDaoFactory.getInstance(IndexerType.SYSLOG, descriptor.host, descriptor.port, descriptor.key, + descriptor.username, descriptor.password)).thenReturn(memoryDao); + slave = jenkins.createSlave(); + slave.setLabelString("myLabel"); + project = jenkins.createFreeStyleProject(); + + } + + @Test + public void test_buildWrapperOnMaster() throws Exception + { + project.getBuildWrappersList().add(new LogstashBuildWrapper()); + QueueTaskFuture f = project.scheduleBuild2(0); + FreeStyleBuild build = f.get(); + assertThat(build.getResult(), equalTo(Result.SUCCESS)); + List dataLines = memoryDao.getOutput(); + assertThat(dataLines.size(), is(3)); + JSONObject firstLine = dataLines.get(0); + JSONObject lastLine = dataLines.get(dataLines.size()-1); + JSONObject data = firstLine.getJSONObject("data"); + assertThat(data.getString("buildHost"),equalTo("Jenkins")); + assertThat(data.getString("buildLabel"),equalTo("master")); + assertThat(lastLine.getJSONArray("message").get(0).toString(),equalTo("Finished: SUCCESS")); + } + + @Test + public void test_buildWrapperOnSlave() throws Exception + { + project.getBuildWrappersList().add(new LogstashBuildWrapper()); + project.setAssignedNode(slave); + + QueueTaskFuture f = project.scheduleBuild2(0); + FreeStyleBuild build = f.get(); + assertThat(build.getResult(), equalTo(Result.SUCCESS)); + List dataLines = memoryDao.getOutput(); + assertThat(dataLines.size(), is(3)); + JSONObject firstLine = dataLines.get(0); + JSONObject lastLine = dataLines.get(dataLines.size()-1); + JSONObject data = firstLine.getJSONObject("data"); + assertThat(data.getString("buildHost"),equalTo(slave.getDisplayName())); + assertThat(data.getString("buildLabel"),equalTo(slave.getLabelString())); + assertThat(lastLine.getJSONArray("message").get(0).toString(),equalTo("Finished: SUCCESS")); + } + + @Test + public void test_buildNotifierOnMaster() throws Exception + { + project.getPublishersList().add(new LogstashNotifier(10, false)); + QueueTaskFuture f = project.scheduleBuild2(0); + FreeStyleBuild build = f.get(); + assertThat(build.getResult(), equalTo(Result.SUCCESS)); + List dataLines = memoryDao.getOutput(); + assertThat(dataLines.size(), is(1)); + JSONObject firstLine = dataLines.get(0); + JSONObject data = firstLine.getJSONObject("data"); + assertThat(data.getString("buildHost"),equalTo("Jenkins")); + assertThat(data.getString("buildLabel"),equalTo("master")); + } + + @Test + public void test_buildNotifierOnSlave() throws Exception + { + project.getPublishersList().add(new LogstashNotifier(10, false)); + project.setAssignedNode(slave); + QueueTaskFuture f = project.scheduleBuild2(0); + FreeStyleBuild build = f.get(); + assertThat(build.getResult(), equalTo(Result.SUCCESS)); + List dataLines = memoryDao.getOutput(); + assertThat(dataLines.size(), is(1)); + JSONObject firstLine = dataLines.get(0); + JSONObject data = firstLine.getJSONObject("data"); + assertThat(data.getString("buildHost"),equalTo(slave.getDisplayName())); + assertThat(data.getString("buildLabel"),equalTo(slave.getLabelString())); + } + + private static class MemoryDao extends AbstractLogstashIndexerDao + { + List output = new ArrayList<>(); + + public MemoryDao() + { + super("localhost", 1, "key", "username", "password"); + } + + @Override + public IndexerType getIndexerType() + { + // TODO Auto-generated method stub + return null; + } + + @Override + public void push(String data) throws IOException + { + JSONObject json = JSONObject.fromObject(data); + output.add(json); + } + + public List getOutput() + { + return output; + } + } +} diff --git a/src/test/java/jenkins/plugins/logstash/LogstashNotifierTest.java b/src/test/java/jenkins/plugins/logstash/LogstashNotifierTest.java index 27a30376..9769748a 100644 --- a/src/test/java/jenkins/plugins/logstash/LogstashNotifierTest.java +++ b/src/test/java/jenkins/plugins/logstash/LogstashNotifierTest.java @@ -17,7 +17,6 @@ import java.io.IOException; import java.io.OutputStream; import java.io.PrintStream; -import java.util.Arrays; import org.junit.After; import org.junit.Before; @@ -26,7 +25,7 @@ import org.mockito.Mock; import org.mockito.Mockito; import org.mockito.invocation.InvocationOnMock; -import org.mockito.runners.MockitoJUnitRunner; +import org.mockito.junit.MockitoJUnitRunner; import org.mockito.stubbing.Answer; @SuppressWarnings("rawtypes") @@ -76,18 +75,21 @@ public Result getResult() { @Mock LogstashWriter mockWriter; @Mock Launcher mockLauncher; @Mock BuildListener mockListener; + @Mock AbstractProject mockProject; ByteArrayOutputStream errorBuffer; PrintStream errorStream; LogstashNotifier notifier; MockRun mockRun; + @Before public void before() throws Exception { errorBuffer = new ByteArrayOutputStream(); errorStream = new PrintStream(errorBuffer, true); - mockRun = new MockRun(mock(AbstractProject.class)); + when(mockProject.assignBuildNumber()).thenReturn(1); + mockRun = new MockRun(mockProject); when(mockListener.getLogger()).thenReturn(errorStream); diff --git a/src/test/java/jenkins/plugins/logstash/LogstashWriterTest.java b/src/test/java/jenkins/plugins/logstash/LogstashWriterTest.java index 8e643e39..735a6178 100644 --- a/src/test/java/jenkins/plugins/logstash/LogstashWriterTest.java +++ b/src/test/java/jenkins/plugins/logstash/LogstashWriterTest.java @@ -2,6 +2,8 @@ import hudson.EnvVars; import hudson.model.AbstractBuild; +import hudson.model.Computer; +import hudson.model.Executor; import hudson.model.Project; import hudson.model.Result; import hudson.model.TaskListener; @@ -15,7 +17,7 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.*; -import org.mockito.runners.MockitoJUnitRunner; +import org.mockito.junit.MockitoJUnitRunner; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -75,6 +77,9 @@ String getJenkinsUrl() { @Mock BuildData mockBuildData; @Mock TaskListener mockListener; + @Mock Computer mockComputer; + @Mock Executor mockExecutor; + @Captor ArgumentCaptor> logLinesCaptor; @@ -85,7 +90,6 @@ public void before() throws Exception { when(mockBuild.getDisplayName()).thenReturn("LogstashNotifierTest"); when(mockBuild.getProject()).thenReturn(mockProject); when(mockBuild.getParent()).thenReturn(mockProject); - when(mockBuild.getBuiltOn()).thenReturn(null); when(mockBuild.getNumber()).thenReturn(123456); when(mockBuild.getTimestamp()).thenReturn(new GregorianCalendar()); when(mockBuild.getRootBuild()).thenReturn(mockBuild); @@ -93,10 +97,12 @@ public void before() throws Exception { when(mockBuild.getSensitiveBuildVariables()).thenReturn(Collections.emptySet()); when(mockBuild.getEnvironments()).thenReturn(null); when(mockBuild.getAction(AbstractTestResultAction.class)).thenReturn(mockTestResultAction); - when(mockBuild.getLog(0)).thenReturn(Arrays.asList()); when(mockBuild.getLog(3)).thenReturn(Arrays.asList("line 1", "line 2", "line 3", "Log truncated...")); - when(mockBuild.getLog(Integer.MAX_VALUE)).thenReturn(Arrays.asList("line 1", "line 2", "line 3", "line 4")); when(mockBuild.getEnvironment(null)).thenReturn(new EnvVars()); + when(mockBuild.getExecutor()).thenReturn(mockExecutor); + when(mockExecutor.getOwner()).thenReturn(mockComputer); + when(mockComputer.getNode()).thenReturn(null); + when(mockTestResultAction.getTotalCount()).thenReturn(0); when(mockTestResultAction.getSkipCount()).thenReturn(0); @@ -142,7 +148,7 @@ public void constructorSuccess() throws Exception { verify(mockBuild).getDescription(); verify(mockBuild).getUrl(); verify(mockBuild).getAction(AbstractTestResultAction.class); - verify(mockBuild).getBuiltOn(); + verify(mockBuild).getExecutor(); verify(mockBuild, times(2)).getNumber(); verify(mockBuild).getTimestamp(); verify(mockBuild, times(4)).getRootBuild(); diff --git a/src/test/java/jenkins/plugins/logstash/persistence/BuildDataTest.java b/src/test/java/jenkins/plugins/logstash/persistence/BuildDataTest.java index 51dfb09b..2e445b21 100644 --- a/src/test/java/jenkins/plugins/logstash/persistence/BuildDataTest.java +++ b/src/test/java/jenkins/plugins/logstash/persistence/BuildDataTest.java @@ -23,13 +23,15 @@ import org.mockito.Mock; import org.mockito.Mockito; import org.mockito.invocation.InvocationOnMock; -import org.mockito.runners.MockitoJUnitRunner; +import org.mockito.junit.MockitoJUnitRunner; import org.mockito.stubbing.Answer; import hudson.EnvVars; import hudson.model.AbstractBuild; +import hudson.model.Computer; import hudson.model.Environment; import hudson.model.EnvironmentList; +import hudson.model.Executor; import hudson.model.Node; import hudson.model.Project; import hudson.model.Result; @@ -61,6 +63,8 @@ public class BuildDataTest { @Mock Environment mockEnvironment; @Mock Date mockDate; @Mock TaskListener mockListener; + @Mock Computer mockComputer; + @Mock Executor mockExecutor; @Before @@ -69,7 +73,6 @@ public void before() throws Exception { when(mockBuild.getDisplayName()).thenReturn("BuildData Test"); when(mockBuild.getFullDisplayName()).thenReturn("BuildData Test #123456"); when(mockBuild.getDescription()).thenReturn("Mock project for testing BuildData"); - when(mockBuild.getProject()).thenReturn(mockProject); when(mockBuild.getParent()).thenReturn(mockProject); when(mockBuild.getNumber()).thenReturn(123456); when(mockBuild.getTimestamp()).thenReturn(new GregorianCalendar()); @@ -97,6 +100,8 @@ public void before() throws Exception { when(mockRootProject.getFullName()).thenReturn("parent/RootBuildDataTest"); when(mockDate.getTime()).thenReturn(60L); + when(mockBuild.getExecutor()).thenReturn(mockExecutor); + when(mockExecutor.getOwner()).thenReturn(mockComputer); } @After @@ -124,7 +129,7 @@ private void verifyMocks() throws Exception verify(mockBuild).getStartTimeInMillis(); verify(mockBuild).getUrl(); verify(mockBuild).getAction(AbstractTestResultAction.class); - verify(mockBuild).getBuiltOn(); + verify(mockBuild).getExecutor(); verify(mockBuild).getNumber(); verify(mockBuild).getTimestamp(); verify(mockBuild, times(4)).getRootBuild(); @@ -133,6 +138,8 @@ private void verifyMocks() throws Exception verify(mockBuild).getEnvironments(); verify(mockBuild).getEnvironment(mockListener); + verify(mockExecutor).getOwner(); + verify(mockRootProject).getName(); verify(mockRootProject).getFullName(); @@ -150,9 +157,15 @@ private void verifyTestResultActions() { verify(mockTestResultAction, times(1)).getFailedTests(); } + private void verifiyNodeActions(int labelCount) { + verify(mockComputer).getNode(); + verify(mockNode, times(2)).getDisplayName(); + verify(mockNode, times(labelCount)).getLabelString(); + } + @Test public void constructorSuccessBuiltOnNull() throws Exception { - when(mockBuild.getBuiltOn()).thenReturn(null); + when(mockComputer.getNode()).thenReturn(null); // Unit under test BuildData buildData = new BuildData(mockBuild, mockDate, mockListener); @@ -170,7 +183,7 @@ public void constructorSuccessBuiltOnNull() throws Exception { @Test public void constructorSuccessBuiltOnMaster() throws Exception { - when(mockBuild.getBuiltOn()).thenReturn(mockNode); + when(mockComputer.getNode()).thenReturn(mockNode); when(mockNode.getDisplayName()).thenReturn("Jenkins"); when(mockNode.getLabelString()).thenReturn(""); @@ -187,11 +200,12 @@ public void constructorSuccessBuiltOnMaster() throws Exception { verifyMocks(); verifyTestResultActions(); + verifiyNodeActions(1); } @Test public void constructorSuccessBuiltOnSlave() throws Exception { - when(mockBuild.getBuiltOn()).thenReturn(mockNode); + when(mockComputer.getNode()).thenReturn(mockNode); when(mockNode.getDisplayName()).thenReturn("Test Slave 01"); when(mockNode.getLabelString()).thenReturn("Test Slave"); @@ -208,6 +222,7 @@ public void constructorSuccessBuiltOnSlave() throws Exception { verifyMocks(); verifyTestResultActions(); + verifiyNodeActions(2); } @Test @@ -252,8 +267,7 @@ public void constructorSuccessWithEnvVars() throws Exception { when(mockBuild.getEnvironments()).thenReturn(new EnvironmentList(Arrays.asList(mockEnvironment))); when(mockBuild.getBuildVariables()).thenReturn(new HashMap()); - when(mockBuild.getBuiltOn()).thenReturn(mockNode); - + when(mockComputer.getNode()).thenReturn(mockNode); when(mockNode.getDisplayName()).thenReturn("Jenkins"); when(mockNode.getLabelString()).thenReturn(""); @@ -289,6 +303,7 @@ public Void answer(InvocationOnMock invocation) throws Throwable { verifyMocks(); verifyTestResultActions(); + verifiyNodeActions(1); } @Test // JENKINS-41324 @@ -297,8 +312,7 @@ public void constructorSuccessWithChangedEnvVars() throws Exception { when(mockBuild.getBuildVariables()).thenReturn(new HashMap()); when(mockBuild.getSensitiveBuildVariables()).thenReturn(new HashSet()); - when(mockBuild.getBuiltOn()).thenReturn(mockNode); - + when(mockComputer.getNode()).thenReturn(mockNode); when(mockNode.getDisplayName()).thenReturn("Jenkins"); when(mockNode.getLabelString()).thenReturn(""); @@ -327,6 +341,7 @@ public Void answer(InvocationOnMock invocation) throws Throwable { verifyMocks(); verifyTestResultActions(); + verifiyNodeActions(1); } @Test