From f38a7d4b998b627f8ebad0a2be7dbd886b22c062 Mon Sep 17 00:00:00 2001 From: "Vedran @ vvidovic" Date: Fri, 4 Jan 2013 10:53:32 +0100 Subject: [PATCH 1/3] added customizable RTC accept command output parser (customize with environment variables) --- .../jenkins/plugins/rtc/JazzClient.java | 5 +- .../deluan/jenkins/plugins/rtc/JazzSCM.java | 1 + .../plugins/rtc/commands/AcceptCommand.java | 34 +++++++++++++- .../accept/AcceptCustomOutputParser.java | 24 ++++++++++ .../accept/BaseAcceptOutputParser.java | 26 +++++++++- .../accept/AcceptCustomOutputParserTest.java | 47 +++++++++++++++++++ 6 files changed, 133 insertions(+), 4 deletions(-) create mode 100644 src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParser.java create mode 100644 src/test/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParserTest.java diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzClient.java b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzClient.java index f6c829f..bd19e60 100644 --- a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzClient.java +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzClient.java @@ -154,11 +154,12 @@ public String getVersion() throws IOException, InterruptedException { /** * Call scm accept command.

* - * @return all changeSets accepted, complete with affected paths and related work itens + * @return all changeSets accepted, complete with affected paths and related work items * @throws IOException * @throws InterruptedException */ public List accept() throws IOException, InterruptedException { + logger.fine("accept()"); Map compareCmdResults = compare(); if (!compareCmdResults.isEmpty()) { @@ -174,6 +175,7 @@ public List accept() throws IOException, InterruptedException { } } + logger.fine("accept() end"); return new ArrayList(compareCmdResults.values()); } @@ -195,6 +197,7 @@ private T execute(ParseableCommand cmd) throws IOException, InterruptedEx try { result = cmd.parse(in); } catch (Exception e) { + logger.log(Level.SEVERE, "Error parsing command!", e); throw new IOException(e); } finally { in.close(); diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzSCM.java b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzSCM.java index c8b05a1..0cbeaa2 100644 --- a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzSCM.java +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzSCM.java @@ -136,6 +136,7 @@ public boolean checkout(AbstractBuild build, Launcher launcher, FilePath w try { changes = client.accept(); } catch (IOException e) { + logger.log(Level.WARNING, "Error accepting...", e); return false; } diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommand.java b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommand.java index 60c1c78..a67d70c 100644 --- a/src/main/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommand.java +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommand.java @@ -1,7 +1,9 @@ package com.deluan.jenkins.plugins.rtc.commands; +import com.deluan.jenkins.plugins.rtc.JazzClient; import com.deluan.jenkins.plugins.rtc.JazzConfiguration; import com.deluan.jenkins.plugins.rtc.changelog.JazzChangeSet; +import com.deluan.jenkins.plugins.rtc.commands.accept.AcceptCustomOutputParser; import com.deluan.jenkins.plugins.rtc.commands.accept.AcceptNewOutputParser; import com.deluan.jenkins.plugins.rtc.commands.accept.AcceptOldOutputParser; import com.deluan.jenkins.plugins.rtc.commands.accept.BaseAcceptOutputParser; @@ -13,6 +15,10 @@ import java.util.Collection; import java.util.LinkedHashSet; import java.util.Map; +import java.util.logging.Logger; +import java.util.regex.Pattern; + +import org.springframework.util.StringUtils; /** * @author deluan @@ -20,6 +26,20 @@ public class AcceptCommand extends AbstractCommand implements ParseableCommand> { public static final String NEW_FORMAT_VERSION = "2.1.0"; + + private static final Logger logger = Logger.getLogger(AcceptCommand.class.getName()); + + /* + * Environment properties used for custom rtc command line client output parsing. + * Have to use following values in jenkins windows start bat file for RTC 3.1.100: + * set RTC_ACCEPT_OUT_PATTERN_STARTCHANGESET=^^\s{6}\((\d+)\)\s(.*) + * set RTC_ACCEPT_OUT_PATTERN_FILE=^^\s{10}---(.)-\s+(.*) + * set RTC_ACCEPT_OUT_PATTERN_WORKITEM=^^\s{10}\((\d+)\)+(.*) + */ + public static final String RTC_ACCEPT_OUT_PATTERN_STARTCHANGESET = "RTC_ACCEPT_OUT_PATTERN_STARTCHANGESET"; + public static final String RTC_ACCEPT_OUT_PATTERN_FILE = "RTC_ACCEPT_OUT_PATTERN_FILE"; + public static final String RTC_ACCEPT_OUT_PATTERN_WORKITEM = "RTC_ACCEPT_OUT_PATTERN_WORKITEM"; + private Collection changeSets; private BaseAcceptOutputParser parser; protected boolean oldFormat = false; @@ -28,7 +48,19 @@ public AcceptCommand(JazzConfiguration configurationProvider, Collection super(configurationProvider); this.changeSets = new LinkedHashSet(changeSets); this.oldFormat = (version.compareTo(NEW_FORMAT_VERSION) < 0); - parser = (oldFormat) ? new AcceptOldOutputParser() : new AcceptNewOutputParser(); + + String startChangesetPattern = System.getenv(RTC_ACCEPT_OUT_PATTERN_STARTCHANGESET); + String filePattern = System.getenv(RTC_ACCEPT_OUT_PATTERN_FILE); + String workItemPattern = System.getenv(RTC_ACCEPT_OUT_PATTERN_WORKITEM); + + if(StringUtils.hasText(startChangesetPattern) && StringUtils.hasText(filePattern) && StringUtils.hasText(workItemPattern)) { + logger.info("RTCOUT_* flags found, using AcceptCustomOutputParser('" + startChangesetPattern + "','" + filePattern + "','" + workItemPattern + "')"); + parser = new AcceptCustomOutputParser(startChangesetPattern, filePattern, workItemPattern); + } + else { + logger.info("RTCOUT_* flags not found, oldFormat: " + oldFormat); + parser = (oldFormat) ? new AcceptOldOutputParser() : new AcceptNewOutputParser(); + } } public ArgumentListBuilder getArguments() { diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParser.java b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParser.java new file mode 100644 index 0000000..9147355 --- /dev/null +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParser.java @@ -0,0 +1,24 @@ +package com.deluan.jenkins.plugins.rtc.commands.accept; + +/** + * Configurable with three environment variables: + * RTC_ACCEPT_OUT_PATTERN_STARTCHANGESET, RTC_ACCEPT_OUT_PATTERN_FILE and RTC_ACCEPT_OUT_PATTERN_WORKITEM. + * (proper values for RTC 3.1.100: "^\s{6}\((\d+)\)\s(.*)", "^\s{10}---(.)-\s+(.*)" and "^\s{10}\((\d+)\)+(.*)". + * + * @author vvidovic + */ +public class AcceptCustomOutputParser extends BaseAcceptOutputParser { + public AcceptCustomOutputParser(String startChangesetPattern, String filePattern, String workItemPattern) { + super(startChangesetPattern, filePattern, workItemPattern); + } + + @Override + protected String parseWorkItem(String string) { + return string; + } + + @Override + protected String parseEditFlag(String string) { + return string; + } +} diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/BaseAcceptOutputParser.java b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/BaseAcceptOutputParser.java index 97f63b6..ef946c0 100644 --- a/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/BaseAcceptOutputParser.java +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/commands/accept/BaseAcceptOutputParser.java @@ -1,6 +1,5 @@ package com.deluan.jenkins.plugins.rtc.commands.accept; -import com.deluan.jenkins.plugins.rtc.changelog.JazzChangeSet; import hudson.scm.EditType; import java.io.BufferedReader; @@ -8,13 +7,19 @@ import java.text.ParseException; import java.util.HashMap; import java.util.Map; +import java.util.logging.Level; +import java.util.logging.Logger; import java.util.regex.Matcher; import java.util.regex.Pattern; +import com.deluan.jenkins.plugins.rtc.changelog.JazzChangeSet; + /** * @author deluan */ public abstract class BaseAcceptOutputParser { + private static final Logger logger = Logger.getLogger(BaseAcceptOutputParser.class.getName()); + private Pattern startChangesetPattern; private Pattern filePattern; private Pattern workItemPattern; @@ -27,26 +32,43 @@ public BaseAcceptOutputParser(String startChangesetPattern, String filePattern, public Map parse(BufferedReader reader) throws ParseException, IOException { Map result = new HashMap(); - + + logger.fine("parse()"); String line; JazzChangeSet changeSet = null; Matcher matcher; while ((line = reader.readLine()) != null) { + if(logger.isLoggable(Level.FINER)) { + logger.finer("parse(), line: '" + line + "'"); + } if ((matcher = startChangesetPattern.matcher(line)).matches()) { + if(logger.isLoggable(Level.FINER)) { + logger.finer("startChangeset"); + } if (changeSet != null) { result.put(changeSet.getRev(), changeSet); } changeSet = new JazzChangeSet(); changeSet.setRev(matcher.group(1)); } else if ((matcher = filePattern.matcher(line)).matches()) { + if(logger.isLoggable(Level.FINER)) { + logger.finer("file"); + } assert changeSet != null; String action = parseAction(matcher.group(1)); String path = parsePath(matcher.group(2)); changeSet.addItem(path, action); } else if ((matcher = workItemPattern.matcher(line)).matches()) { + if(logger.isLoggable(Level.FINER)) { + logger.finer("workItem"); + } assert changeSet != null; changeSet.addWorkItem(parseWorkItem(matcher.group(2))); + } else { + if(logger.isLoggable(Level.FINER)) { + logger.finer("line skipped"); + } } } diff --git a/src/test/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParserTest.java b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParserTest.java new file mode 100644 index 0000000..b8d59f8 --- /dev/null +++ b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/accept/AcceptCustomOutputParserTest.java @@ -0,0 +1,47 @@ +package com.deluan.jenkins.plugins.rtc.commands.accept; + +import static org.junit.Assert.*; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.StringReader; +import java.text.ParseException; +import java.util.Map; + +import org.junit.Assert; +import org.junit.Test; + +import com.deluan.jenkins.plugins.rtc.changelog.JazzChangeSet; + +/** + * Test for {@link AcceptCustomOutputParser}. + * @author vvidovic + */ +public class AcceptCustomOutputParserTest { + + public static final int RTCOUT_ACTIONFLAG_POSITION = 3; + public static final String RTCOUT_PATTERN_FILE = "^\\s{10}---(.)-\\s+(.*)"; + public static final String RTCOUT_PATTERN_STARTCHANGESET = "^\\s{6}\\((\\d+)\\)\\s(.*)"; + public static final String RTCOUT_PATTERN_WORKITEM = "^\\s{10}[^\\d\\s]+(\\d+)[^\\d]+(.*)"; + + public static final String TEST_OUT = "Workspace: (1002) \"RTC-workspace\"\n" + +" Component: (1003) \"Stream MavenModule\"\n" + +" Change sets:\n" + +" (1159) ---$ \"jenkins test.\" 03-sij-2013 04:32 PM\n" + +" Changes:\n" + +" ---c- \\MOdule\\3-design\\use-case-realizations\\17-razno\\ucr-something.sequence-diagram\n" + +" Work items:\n" + +" (1134) 49781 \"Osposobiti CI okolinu\""; + + @Test + public void testParse() throws ParseException, IOException { + AcceptCustomOutputParser parser = new AcceptCustomOutputParser(RTCOUT_PATTERN_STARTCHANGESET, RTCOUT_PATTERN_FILE, RTCOUT_PATTERN_WORKITEM); + + StringReader sr = new StringReader(TEST_OUT); + BufferedReader br = new BufferedReader(sr); + Map result = parser.parse(br); + + Assert.assertNotNull(result); + } + +} From 72d58679335068ba6993272c8dbaecbf036ab24a Mon Sep 17 00:00:00 2001 From: "Vedran @ vvidovic" Date: Fri, 4 Jan 2013 10:54:33 +0100 Subject: [PATCH 2/3] misspelling fix: itens to items --- .../plugins/rtc/changelog/JazzChangeSetList/index.jelly | 2 +- .../plugins/rtc/changelog/JazzChangeLogReaderTest.java | 4 ++-- .../jenkins/plugins/rtc/commands/AcceptCommandTest.java | 6 +++--- .../deluan/jenkins/plugins/rtc/commands/CommandTest.java | 2 +- 4 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/main/resources/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeSetList/index.jelly b/src/main/resources/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeSetList/index.jelly index 998532c..2ff9d63 100644 --- a/src/main/resources/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeSetList/index.jelly +++ b/src/main/resources/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeSetList/index.jelly @@ -40,7 +40,7 @@ - ${%Related Work Itens} + ${%Related Work Items} diff --git a/src/test/java/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeLogReaderTest.java b/src/test/java/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeLogReaderTest.java index e332f0e..456f133 100644 --- a/src/test/java/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeLogReaderTest.java +++ b/src/test/java/com/deluan/jenkins/plugins/rtc/changelog/JazzChangeLogReaderTest.java @@ -60,8 +60,8 @@ public void testCompleteChangelog() throws Exception { assertThat("User is incorrect", readChangeSet.getUser(), is(originalChangeSet.getUser())); assertThat("Email is incorrect", readChangeSet.getEmail(), is(originalChangeSet.getEmail())); assertThat("Comment is incorrect", readChangeSet.getMsg(), is(originalChangeSet.getMsg())); - assertThat("Number of itens in changeset is incorrect", readChangeSet.getItems().size(), is(2)); - assertThat("Number of work itens in changeset is incorrect", readChangeSet.getWorkItems().size(), is(1)); + assertThat("Number of items in changeset is incorrect", readChangeSet.getItems().size(), is(2)); + assertThat("Number of work items in changeset is incorrect", readChangeSet.getWorkItems().size(), is(1)); JazzChangeSet.Item item = readChangeSet.getItems().get(0); assertThat("Action is incorrect", item.getAction(), is("delete")); diff --git a/src/test/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommandTest.java b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommandTest.java index b429a25..863c868 100644 --- a/src/test/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommandTest.java +++ b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/AcceptCommandTest.java @@ -45,7 +45,7 @@ public void acceptCommandParse_2_1_0() throws Exception { JazzChangeSet changeSet = result.get("1714"); assertEquals("The number of files in the changesets was incorrect", 8, changeSet.getAffectedPaths().size()); - assertEquals("The number of work itens in the changesets was incorrect", 2, changeSet.getWorkItems().size()); + assertEquals("The number of work items in the changesets was incorrect", 2, changeSet.getWorkItems().size()); JazzChangeSet.Item item = changeSet.getItems().get(0); assertTrue("The file is not the expected one", item.getPath().endsWith("GerenteOferta.java")); @@ -66,7 +66,7 @@ public void acceptCommandParse_Chinese() throws Exception { JazzChangeSet changeSet = result.get("1020"); assertEquals("The number of files in the changesets was incorrect", 2, changeSet.getAffectedPaths().size()); - assertEquals("The number of work itens in the changesets was incorrect", 1, changeSet.getWorkItems().size()); + assertEquals("The number of work items in the changesets was incorrect", 1, changeSet.getWorkItems().size()); JazzChangeSet.Item item = changeSet.getItems().get(0); assertTrue("The file is not the expected one", item.getPath().endsWith("com_tps_eppic_ConfigValues_core_properties")); @@ -83,7 +83,7 @@ public void acceptCommandParse_2_0_2() throws Exception { JazzChangeSet changeSet = result.get("1002"); assertEquals("The number of files in the changesets was incorrect", 5, changeSet.getAffectedPaths().size()); - assertEquals("The number of work itens in the changesets was incorrect", 1, changeSet.getWorkItems().size()); + assertEquals("The number of work items in the changesets was incorrect", 1, changeSet.getWorkItems().size()); JazzChangeSet.Item item = changeSet.getItems().get(3); assertTrue("The file is not the expected one", item.getPath().endsWith("FabricaEJBBean.java")); diff --git a/src/test/java/com/deluan/jenkins/plugins/rtc/commands/CommandTest.java b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/CommandTest.java index a7a1a8b..6beeee1 100644 --- a/src/test/java/com/deluan/jenkins/plugins/rtc/commands/CommandTest.java +++ b/src/test/java/com/deluan/jenkins/plugins/rtc/commands/CommandTest.java @@ -50,7 +50,7 @@ public void listCommandParse() throws Exception { JazzChangeSet changeSet = result.get("1714"); assertEquals("The number of files in the changesets was incorrect", 8, changeSet.getAffectedPaths().size()); - assertEquals("The number of work itens in the changesets was incorrect", 2, changeSet.getWorkItems().size()); + assertEquals("The number of work items in the changesets was incorrect", 2, changeSet.getWorkItems().size()); JazzChangeSet.Item item = changeSet.getItems().get(0); assertTrue("The file is not the expected one", item.getPath().endsWith("GerenteOferta.java")); From 04ad723608edd2fa8cd3d172384650a06d7ce6c5 Mon Sep 17 00:00:00 2001 From: "Vedran @ vvidovic" Date: Fri, 4 Jan 2013 11:48:47 +0100 Subject: [PATCH 3/3] fixed double '/' sign which caused that link to workitem didn't work in Chrome --- .../deluan/jenkins/plugins/rtc/JazzRepositoryBrowser.java | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzRepositoryBrowser.java b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzRepositoryBrowser.java index d0c0dda..5d5d74f 100644 --- a/src/main/java/com/deluan/jenkins/plugins/rtc/JazzRepositoryBrowser.java +++ b/src/main/java/com/deluan/jenkins/plugins/rtc/JazzRepositoryBrowser.java @@ -39,7 +39,11 @@ public URL getChangeSetLink(JazzChangeSet changeSet) throws IOException { // ${repositoryUrl}/resource/itemName/com.ibm.team.workitem.WorkItem/${alias} public URL getWorkItemLink(JazzChangeSet changeSet, String workItem) throws IOException { String[] parts = workItem.split(" "); - String url = getBaseUrlString(changeSet) + "/resource/itemName/com.ibm.team.workitem.WorkItem/" + parts[0]; + String baseUrl = getBaseUrlString(changeSet); + if(baseUrl.endsWith("/")) { + baseUrl = baseUrl.substring(0, baseUrl.length() -1); + } + String url = baseUrl + "/resource/itemName/com.ibm.team.workitem.WorkItem/" + parts[0]; return new URL(url); }