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

enable overrideResolvedIssues #194

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
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
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ junit (
autoResolveIssue: false,
autoUnlinkIssue: false,
additionalAttachments: false,
overrideResolvedIssues: false,
)
]
)
Expand Down Expand Up @@ -120,6 +121,7 @@ Checking **Auto resolve issue** check box will enable an experimental feature. B

If you check the **Auto unlink issues when test passes** check box, this plugin will automatically unlink issues for all the tests changing to passed in new builds.

If you check the **Auto override resolved issues** check box, this plugin will create new issues automatically for failing tests that are linked to already resolved issues.

![image of job config settings](img/job-config1.png)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,10 @@
return JobConfigMapping.getInstance().getAutoUnlinkIssue(getJobName());
}

public boolean getOverrideResolvedIssues() {
return JobConfigMapping.getInstance().getOverrideResolvedIssues(getJobName());

Check warning on line 135 in src/main/java/org/jenkinsci/plugins/JiraTestResultReporter/JiraTestDataPublisher.java

View check run for this annotation

ci.jenkins.io / Code Coverage

Not covered line

Line 135 is not covered by tests
}

/**
* Getter for list of attachments by test method identified by its classname and name
* @param className
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -117,10 +117,6 @@
return autoRaiseIssue;
}

public boolean getOverrideResolvedIssues() {
return overrideResolvedIssues;
}

public boolean getAutoResolveIssue() {
return autoResolveIssue;
}
Expand All @@ -133,342 +129,346 @@
return additionalAttachments;
}

public boolean getOverrideResolvedIssues() {
return overrideResolvedIssues;
}

/**
* Getter for the issue key pattern
* @return
*/
public Pattern getIssueKeyPattern() {
return issueKeyPattern;
}

/**
* Method for resolving transient objects after deserialization. Called by the JVM.
* See Java documentation for more details.
* @return this object
*/
@SuppressFBWarnings(value = "SE_PRIVATE_READ_RESOLVE_NOT_INHERITED", justification = "TODO needs triage")
private Object readResolve() {
compileIssueKeyPattern();
return this;
}

protected void compileIssueKeyPattern() {
this.issueKeyPattern = projectKey != null ? Pattern.compile(projectKey + "-\\d+") : null;
}
}

/**
* Builder fot a JobConfigEntry
* Builder for a JobConfigEntry
*/
public static class JobConfigEntryBuilder extends JobConfigEntry {
/**
* Constructor
*/
public JobConfigEntryBuilder() {
super(null, null, new ArrayList<>(), false, false, false, false, false);
}

public JobConfigEntryBuilder withProjectKey(String projectKey) {
this.projectKey = projectKey;
compileIssueKeyPattern();
return this;
}

public JobConfigEntryBuilder withIssueType(Long issueType) {
this.issueType = issueType;
return this;
}

public JobConfigEntryBuilder withConfigs(List<AbstractFields> configs) {
this.configs = configs;
return this;
}

public JobConfigEntryBuilder withAutoRaiseIssues(boolean autoRaiseIssues) {
this.autoRaiseIssue = autoRaiseIssues;
return this;
}

public JobConfigEntryBuilder withOverrideResolvedIssues(boolean overrideResolvedIssues) {
this.overrideResolvedIssues = overrideResolvedIssues;
return this;
}

public JobConfigEntryBuilder withAutoResolveIssues(boolean autoResolveIssue) {
this.autoResolveIssue = autoResolveIssue;
return this;
}

public JobConfigEntryBuilder withAutoUnlinkIssues(boolean autoUnlinkIssues) {
this.autoUnlinkIssue = autoUnlinkIssues;
return this;
}

public JobConfigEntryBuilder withAdditionalAttachments(boolean additionalAttachments) {
this.additionalAttachments = additionalAttachments;
return this;
}

public JobConfigEntryBuilder withOverrideResolvedIssues(boolean overrideResolvedIssues) {
this.overrideResolvedIssues = overrideResolvedIssues;
return this;
}

public JobConfigEntry build() {
if (projectKey == null) {
throw new IllegalStateException("The Project Key may not be null");
}
if (issueType == null) {
throw new IllegalStateException("The Issue Type may not be null");
}
StringFields summary = null;
StringFields description = null;

for (AbstractFields field : this.getConfigs()) {
if (field instanceof StringFields) {
StringFields stringField = (StringFields) field;
if (stringField.getFieldKey().equals(SUMMARY_FIELD_NAME)) {
summary = stringField;
}
if (stringField.getFieldKey().equals(DESCRIPTION_FIELD_NAME)) {
description = stringField;
}
}
}

if (summary == null) {
this.getConfigs().add(DEFAULT_SUMMARY_FIELD);
}

if (description == null) {
this.getConfigs().add(DEFAULT_DESCRIPTION_FIELD);
}

return this;
}
}

private static JobConfigMapping instance = new JobConfigMapping();
private static final String CONFIGS_FILE = "JiraIssueJobConfigs";

/**
* Getter for the singleton instance
* @return
*/
public static JobConfigMapping getInstance() {
return instance;
}

private HashMap<String, JobConfigEntry> configMap;

/**
* Constructor. Will deserialize the existing map, or will create an empty new one
*/
private JobConfigMapping() {
configMap = new HashMap<String, JobConfigEntry>();

for (Job project : Jenkins.get().getItems(Job.class)) {
JobConfigEntry entry = load(project);
if (entry != null) {
configMap.put(project.getFullName(), entry);
}
}
}

/**
* Constructs the path for the config file
* @param project
* @return
*/
private String getPathToFile(Job project) {
return project.getRootDir().toPath().resolve(CONFIGS_FILE).toString();
}

private String getPathToJsonFile(Job project) {
return project.getRootDir().toPath().resolve(CONFIGS_FILE).toString() + ".json";
}

/**
* Looks for configurations from a previous version of the plugin and tries to load them
* and save them in the new format
* @param project
* @return the loaded JobConfigEntry, or null if there was no file, or it could not be loaded
*/
private JobConfigEntry loadBackwardsCompatible(Job project) {
try {
FileInputStream fileIn = new FileInputStream(getPathToFile(project));
ObjectInputStream in = new ObjectInputStream(fileIn);
JobConfigEntry entry = (JobConfigEntry) in.readObject();
in.close();
fileIn.close();
JiraUtils.log(
"Found and successfully loaded configs from a previous version for job: " + project.getFullName());
// make sure we have the configurations from previous versions in the new format
save(project, entry);
return entry;
} catch (FileNotFoundException e) {
// Nothing to do
} catch (Exception e) {
JiraUtils.logError(
"ERROR: Found configs from a previous version, but was unable to load them for project "
+ project.getFullName(),
e);
}
return null;
}

/**
* Loads the JobConfigEntry from the file associated with the project
* @param project
* @return the loaded JobConfigEntry, or null if there was no file, or it could not be loaded
*/
private JobConfigEntry load(Job project) {
JobConfigEntry entry = null;
try {
Gson gson = new GsonBuilder()
.registerTypeAdapter(AbstractFields.class, new FieldConfigsJsonAdapter())
.create();
FileInputStream fileIn = new FileInputStream(getPathToJsonFile(project));
JsonReader reader = new JsonReader(new InputStreamReader(fileIn, "UTF-8"));

entry = gson.fromJson(reader, JobConfigEntry.class);
reader.close();
fileIn.close();

return (JobConfigEntry) entry.readResolve();
} catch (FileNotFoundException e) {
entry = loadBackwardsCompatible(project);
if (entry == null) {
JiraUtils.log("No configs found for project " + project.getFullName());
}
} catch (Exception e) {
JiraUtils.logError("ERROR: Could not load configs for project " + project.getFullName(), e);
}
return entry;
}

/**
* Method for saving the map, called every time the map changes
*/
private void save(Job project, JobConfigEntry entry) {
try {
Gson gson = new GsonBuilder()
.registerTypeAdapter(AbstractFields.class, new FieldConfigsJsonAdapter())
.create();
FileOutputStream fileOut = new FileOutputStream(getPathToJsonFile(project));
JsonWriter writer = new JsonWriter(new OutputStreamWriter(fileOut, "UTF-8"));
writer.setIndent(" ");
gson.toJson(entry, JobConfigEntry.class, writer);
writer.close();
fileOut.close();
} catch (Exception e) {
JiraUtils.logError("ERROR: Could not save project map", e);
}
}

/**
* Method for setting the last configuration made for a project
* @param project
* @param projectKey
* @param issueType
* @param configs
*/
public synchronized void saveConfig(
Job project,
String projectKey,
Long issueType,
List<AbstractFields> configs,
boolean autoRaiseIssue,
boolean autoResolveIssue,
boolean autoUnlinkIssue,
boolean overrideResolvedIssues,
boolean additionalAttachments) {
JobConfigEntry entry = new JobConfigEntry(
projectKey,
issueType,
configs,
autoRaiseIssue,
autoResolveIssue,
autoUnlinkIssue,
overrideResolvedIssues,
additionalAttachments);
saveConfig(project, entry);
}

/**
* Method for setting the last configuration made for a project
*/
public synchronized void saveConfig(Job project, JobConfigEntry entry) {
if (entry instanceof JobConfigEntryBuilder) {
entry = ((JobConfigEntryBuilder) entry).build();
}
configMap.put(project.getFullName(), entry);
save(project, entry);
}

private JobConfigEntry getJobConfigEntry(@CheckForNull Job project) {
if (project == null) {
return null;
}
if (!configMap.containsKey(project.getFullName())) {
JobConfigEntry entry = load(project);
if (entry != null) {
configMap.put(project.getFullName(), entry);
}
}
return configMap.get(project.getFullName());
}

/**
* Getter for the last configured fields
* @param project
* @return
*/
public List<AbstractFields> getConfig(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getConfigs() : null;
}

/**
* Getter for the last configured issue type
* @param project
* @return
*/
public Long getIssueType(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getIssueType() : null;
}

/**
* Getter for the last configured project key
* @param project
* @return
*/
public String getProjectKey(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getProjectKey() : null;
}

public boolean getAutoRaiseIssue(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getAutoRaiseIssue() : false;
}

public boolean getOverrideResolvedIssues(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getOverrideResolvedIssues() : false;
}

public boolean getAutoResolveIssue(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getAutoResolveIssue() : false;
}

public boolean getAutoUnlinkIssue(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getAutoUnlinkIssue() : false;
}

public boolean getAdditionalAttachments(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getAdditionalAttachments() : false;
}

public boolean getOverrideResolvedIssues(Job project) {
JobConfigEntry entry = getJobConfigEntry(project);
return entry != null ? entry.getOverrideResolvedIssues() : false;

Check warning on line 469 in src/main/java/org/jenkinsci/plugins/JiraTestResultReporter/JobConfigMapping.java

View check run for this annotation

ci.jenkins.io / Code Coverage

Not covered lines

Lines 133-469 are not covered by tests
}

/**
* Getter for the issue key pattern, used to validate user input
* @param project
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,10 @@
<f:checkbox/>
</f:entry>

<f:entry title="Auto override resolved issues" field="overrideResolvedIssues">
<f:checkbox/>
</f:entry>

<f:advanced>
<j:set var="items" value="${ instance.configs != null ? instance.configs : descriptor.templates }"/>
<f:entry field="configs">
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
<div>
Create issues automatically for failing tests that are linked to resolved issues in JiraIssueKeyToTestMap.json.
Create issues automatically for failing tests that are linked to resolved issues (Stored by jenkins in JiraIssueKeyToTestMap.json).
</div>