未验证 提交 caf3e080 编写于 作者: J Jesse Glick

[JENKINS-52665] Treat plugin dependency mismatches involving snapshots as nonfatal.

上级 d71ac6ff
...@@ -36,7 +36,6 @@ import jenkins.model.Jenkins; ...@@ -36,7 +36,6 @@ import jenkins.model.Jenkins;
import hudson.model.UpdateCenter; import hudson.model.UpdateCenter;
import hudson.model.UpdateSite; import hudson.model.UpdateSite;
import hudson.util.VersionNumber; import hudson.util.VersionNumber;
import org.jvnet.localizer.ResourceBundleHolder;
import org.kohsuke.accmod.Restricted; import org.kohsuke.accmod.Restricted;
import org.kohsuke.accmod.restrictions.DoNotUse; import org.kohsuke.accmod.restrictions.DoNotUse;
import org.kohsuke.accmod.restrictions.NoExternalUse; import org.kohsuke.accmod.restrictions.NoExternalUse;
...@@ -54,7 +53,6 @@ import javax.annotation.CheckForNull; ...@@ -54,7 +53,6 @@ import javax.annotation.CheckForNull;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
import java.io.Closeable; import java.io.Closeable;
import java.io.File; import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.OutputStream; import java.io.OutputStream;
import java.net.URL; import java.net.URL;
...@@ -64,7 +62,6 @@ import java.util.Collection; ...@@ -64,7 +62,6 @@ import java.util.Collection;
import java.util.Collections; import java.util.Collections;
import java.util.Enumeration; import java.util.Enumeration;
import java.util.HashMap; import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
...@@ -600,7 +597,7 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject { ...@@ -600,7 +597,7 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject {
} else { } else {
VersionNumber actualVersion = Jenkins.getVersion(); VersionNumber actualVersion = Jenkins.getVersion();
if (actualVersion.isOlderThan(new VersionNumber(requiredCoreVersion))) { if (actualVersion.isOlderThan(new VersionNumber(requiredCoreVersion))) {
dependencyErrors.put(Messages.PluginWrapper_obsoleteCore(Jenkins.getVersion().toString(), requiredCoreVersion), false); versionDependencyError(Messages.PluginWrapper_obsoleteCore(Jenkins.getVersion().toString(), requiredCoreVersion), Jenkins.getVersion().toString(), requiredCoreVersion);
} }
} }
} }
...@@ -618,11 +615,11 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject { ...@@ -618,11 +615,11 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject {
} else { } else {
if (dependency.isActive()) { if (dependency.isActive()) {
if (isDependencyObsolete(d, dependency)) { if (isDependencyObsolete(d, dependency)) {
dependencyErrors.put(Messages.PluginWrapper_obsolete(dependency.getLongName(), dependency.getVersion(), d.version), false); versionDependencyError(Messages.PluginWrapper_obsolete(dependency.getLongName(), dependency.getVersion(), d.version), dependency.getVersion(), d.version);
} }
} else { } else {
if (isDependencyObsolete(d, dependency)) { if (isDependencyObsolete(d, dependency)) {
dependencyErrors.put(Messages.PluginWrapper_disabledAndObsolete(dependency.getLongName(), dependency.getVersion(), d.version), false); versionDependencyError(Messages.PluginWrapper_disabledAndObsolete(dependency.getLongName(), dependency.getVersion(), d.version), dependency.getVersion(), d.version);
} else { } else {
dependencyErrors.put(Messages.PluginWrapper_disabled(dependency.getLongName()), false); dependencyErrors.put(Messages.PluginWrapper_disabled(dependency.getLongName()), false);
} }
...@@ -635,7 +632,7 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject { ...@@ -635,7 +632,7 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject {
PluginWrapper dependency = parent.getPlugin(d.shortName); PluginWrapper dependency = parent.getPlugin(d.shortName);
if (dependency != null && dependency.isActive()) { if (dependency != null && dependency.isActive()) {
if (isDependencyObsolete(d, dependency)) { if (isDependencyObsolete(d, dependency)) {
dependencyErrors.put(Messages.PluginWrapper_obsolete(dependency.getLongName(), dependency.getVersion(), d.version), false); versionDependencyError(Messages.PluginWrapper_obsolete(dependency.getLongName(), dependency.getVersion(), d.version), dependency.getVersion(), d.version);
} else { } else {
dependencies.add(d); dependencies.add(d);
} }
...@@ -660,6 +657,26 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject { ...@@ -660,6 +657,26 @@ public class PluginWrapper implements Comparable<PluginWrapper>, ModelObject {
return ENABLE_PLUGIN_DEPENDENCIES_VERSION_CHECK && dependency.getVersionNumber().isOlderThan(new VersionNumber(d.version)); return ENABLE_PLUGIN_DEPENDENCIES_VERSION_CHECK && dependency.getVersionNumber().isOlderThan(new VersionNumber(d.version));
} }
/**
* Called when there appears to be a core or plugin version which is too old for a stated dependency.
* Normally records an error in {@link #dependencyErrors}.
* But if one or both versions {@link #isSnapshot}, just issue a warning (JENKINS-52665).
*/
private void versionDependencyError(String message, String actual, String minimum) {
if (isSnapshot(actual) || isSnapshot(minimum)) {
LOGGER.log(WARNING, "Suppressing dependency error in {0} v{1}: {2}", new Object[] {getLongName(), getVersion(), message});
} else {
dependencyErrors.put(message, false);
}
}
/**
* Similar to {@code org.apache.maven.artifact.ArtifactUtils.isSnapshot}.
*/
static boolean isSnapshot(@Nonnull String version) {
return version.contains("-SNAPSHOT") || version.matches(".+-[0-9]{8}.[0-9]{6}-[0-9]+");
}
/** /**
* If the plugin has {@link #getUpdateInfo() an update}, * If the plugin has {@link #getUpdateInfo() an update},
* returns the {@link hudson.model.UpdateSite.Plugin} object. * returns the {@link hudson.model.UpdateSite.Plugin} object.
......
...@@ -15,9 +15,8 @@ import org.mockito.invocation.InvocationOnMock; ...@@ -15,9 +15,8 @@ import org.mockito.invocation.InvocationOnMock;
import org.mockito.stubbing.Answer; import org.mockito.stubbing.Answer;
import static org.hamcrest.CoreMatchers.containsString; import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.MatcherAssert.assertThat; import static org.junit.Assert.*;
import static org.junit.Assert.assertEquals; import org.jvnet.hudson.test.Issue;
import static org.junit.Assert.fail;
import static org.mockito.Matchers.any; import static org.mockito.Matchers.any;
import static org.mockito.Mockito.mock; import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when; import static org.mockito.Mockito.when;
...@@ -180,4 +179,16 @@ public class PluginWrapperTest { ...@@ -180,4 +179,16 @@ public class PluginWrapperTest {
); );
} }
} }
@Issue("JENKINS-52665")
@Test
public void isSnapshot() {
assertFalse(PluginWrapper.isSnapshot("1.0"));
assertFalse(PluginWrapper.isSnapshot("1.0-alpha-1"));
assertFalse(PluginWrapper.isSnapshot("1.0-rc9999.abc123def456"));
assertTrue(PluginWrapper.isSnapshot("1.0-SNAPSHOT"));
assertTrue(PluginWrapper.isSnapshot("1.0-20180719.153600-1"));
assertTrue(PluginWrapper.isSnapshot("1.0-SNAPSHOT (private-abcd1234-jqhacker)"));
}
} }
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册