From 52acfa962fcd118fe8a75bc9a80719a71485f743 Mon Sep 17 00:00:00 2001 From: Basil Crow Date: Sat, 15 May 2021 22:27:32 -0700 Subject: [PATCH] Remove usages of deprecated (in Java 9 and above) `Class#newInstance` (#5483) * Remove usages of deprecated (in Java 9 and above) `Class#newInstance` * Improve catching of InvocationTargetException * Use AssertionError where appropriate --- .../java/hudson/ClassicPluginStrategy.java | 5 +++-- core/src/main/java/hudson/cli/CLICommand.java | 7 ++++--- core/src/main/java/hudson/cli/Connection.java | 2 +- .../main/java/hudson/lifecycle/Lifecycle.java | 21 ++++++++++++++++++- .../main/java/hudson/model/ComputerSet.java | 5 +++-- .../main/java/hudson/model/Descriptor.java | 9 ++++---- .../java/hudson/util/DescribableList.java | 21 ++++++++++++++++++- .../main/java/hudson/util/PersistedList.java | 21 ++++++++++++++++++- .../jenkins/ClassLoaderReflectionToolkit.java | 10 ++++----- .../jenkins/model/lazy/LazyBuildMixIn.java | 4 ++-- .../util/AntWithFindResourceClassLoader.java | 2 +- .../hudson/util/SubClassGeneratorTest.java | 2 +- .../tools/ZipExtractionInstallerTest.java | 2 +- 13 files changed, 85 insertions(+), 26 deletions(-) diff --git a/core/src/main/java/hudson/ClassicPluginStrategy.java b/core/src/main/java/hudson/ClassicPluginStrategy.java index de4b40a75edb..5b584e5de774 100644 --- a/core/src/main/java/hudson/ClassicPluginStrategy.java +++ b/core/src/main/java/hudson/ClassicPluginStrategy.java @@ -31,6 +31,7 @@ import hudson.util.CyclicGraphDetector.CycleDetectedException; import hudson.util.IOUtils; import hudson.util.MaskingClassLoader; +import java.lang.reflect.InvocationTargetException; import jenkins.ClassLoaderReflectionToolkit; import jenkins.ExtensionFilter; import jenkins.plugins.DetachedPluginsUtil; @@ -379,14 +380,14 @@ public void load(PluginWrapper wrapper) throws IOException { } else { try { Class clazz = wrapper.classLoader.loadClass(className); - Object o = clazz.newInstance(); + Object o = clazz.getDeclaredConstructor().newInstance(); if(!(o instanceof Plugin)) { throw new IOException(className+" doesn't extend from hudson.Plugin"); } wrapper.setPlugin((Plugin) o); } catch (LinkageError | ClassNotFoundException e) { throw new IOException("Unable to load " + className + " from " + wrapper.getShortName(),e); - } catch (IllegalAccessException | InstantiationException e) { + } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { throw new IOException("Unable to create instance of " + className + " from " + wrapper.getShortName(),e); } } diff --git a/core/src/main/java/hudson/cli/CLICommand.java b/core/src/main/java/hudson/cli/CLICommand.java index d0c9825768e2..22bca9823586 100644 --- a/core/src/main/java/hudson/cli/CLICommand.java +++ b/core/src/main/java/hudson/cli/CLICommand.java @@ -40,6 +40,7 @@ import java.io.IOException; import java.io.InputStream; import java.io.PrintStream; +import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Type; import java.nio.charset.Charset; import java.util.List; @@ -481,9 +482,9 @@ protected String getClientEnvironmentVariable(String name) throws IOException, I */ protected CLICommand createClone() { try { - return getClass().newInstance(); - } catch (IllegalAccessException | InstantiationException e) { - throw new AssertionError(e); + return getClass().getDeclaredConstructor().newInstance(); + } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { + throw new LinkageError(e.getMessage(), e); } } diff --git a/core/src/main/java/hudson/cli/Connection.java b/core/src/main/java/hudson/cli/Connection.java index 13cec3f6159f..85fb25d58cb9 100644 --- a/core/src/main/java/hudson/cli/Connection.java +++ b/core/src/main/java/hudson/cli/Connection.java @@ -268,7 +268,7 @@ public PublicKey verifyIdentity(byte[] sharedSecret) throws IOException, General return spk; } catch (ClassNotFoundException e) { - throw new Error(e); // impossible + throw new AssertionError(e); // impossible } } diff --git a/core/src/main/java/hudson/lifecycle/Lifecycle.java b/core/src/main/java/hudson/lifecycle/Lifecycle.java index 152f4d457b5c..f55d42bcd30c 100644 --- a/core/src/main/java/hudson/lifecycle/Lifecycle.java +++ b/core/src/main/java/hudson/lifecycle/Lifecycle.java @@ -25,6 +25,8 @@ import hudson.ExtensionPoint; import hudson.Functions; +import java.io.UncheckedIOException; +import java.lang.reflect.InvocationTargetException; import jenkins.util.SystemProperties; import hudson.Util; import jenkins.model.Jenkins; @@ -62,7 +64,11 @@ public static synchronized Lifecycle get() { if(p!=null) { try { ClassLoader cl = Jenkins.get().getPluginManager().uberClassLoader; - instance = (Lifecycle)cl.loadClass(p).newInstance(); + instance = (Lifecycle)cl.loadClass(p).getDeclaredConstructor().newInstance(); + } catch (NoSuchMethodException e) { + NoSuchMethodError x = new NoSuchMethodError(e.getMessage()); + x.initCause(e); + throw x; } catch (InstantiationException e) { InstantiationError x = new InstantiationError(e.getMessage()); x.initCause(e); @@ -75,6 +81,19 @@ public static synchronized Lifecycle get() { NoClassDefFoundError x = new NoClassDefFoundError(e.getMessage()); x.initCause(e); throw x; + } catch (InvocationTargetException e) { + Throwable t = e.getCause(); + if (t instanceof RuntimeException) { + throw (RuntimeException) t; + } else if (t instanceof IOException) { + throw new UncheckedIOException((IOException) t); + } else if (t instanceof Exception) { + throw new RuntimeException(t); + } else if (t instanceof Error) { + throw (Error) t; + } else { + throw new Error(e); + } } } else { if(Functions.isWindows()) { diff --git a/core/src/main/java/hudson/model/ComputerSet.java b/core/src/main/java/hudson/model/ComputerSet.java index 9ffcdfc80e0d..cbeb58bae1ae 100644 --- a/core/src/main/java/hudson/model/ComputerSet.java +++ b/core/src/main/java/hudson/model/ComputerSet.java @@ -37,6 +37,7 @@ import hudson.util.DescribableList; import hudson.util.FormApply; import hudson.util.FormValidation; +import java.lang.reflect.InvocationTargetException; import jenkins.model.Jenkins; import jenkins.model.ModelObjectWithChildren; import jenkins.model.ModelObjectWithContextMenu.ContextMenu; @@ -474,10 +475,10 @@ public static List getComputerNames() { private static NodeMonitor createDefaultInstance(Descriptor d, boolean ignored) { try { - NodeMonitor nm = d.clazz.newInstance(); + NodeMonitor nm = d.clazz.getDeclaredConstructor().newInstance(); nm.setIgnored(ignored); return nm; - } catch (InstantiationException | IllegalAccessException e) { + } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { LOGGER.log(Level.SEVERE, "Failed to instantiate "+d.clazz,e); } return null; diff --git a/core/src/main/java/hudson/model/Descriptor.java b/core/src/main/java/hudson/model/Descriptor.java index 2faecefa0335..e307c1acd7ba 100644 --- a/core/src/main/java/hudson/model/Descriptor.java +++ b/core/src/main/java/hudson/model/Descriptor.java @@ -37,6 +37,7 @@ import hudson.util.ReflectionUtils; import hudson.util.ReflectionUtils.Parameter; import hudson.views.ListViewColumn; +import java.lang.reflect.InvocationTargetException; import jenkins.model.GlobalConfiguration; import jenkins.model.GlobalConfigurationCategory; import jenkins.model.Jenkins; @@ -589,7 +590,7 @@ public T newInstance(@Nullable StaplerRequest req, @NonNull JSONObject formData) } else { if (req==null) { // yes, req is supposed to be always non-null, but see the note above - return verifyNewInstance(clazz.newInstance()); + return verifyNewInstance(clazz.getDeclaredConstructor().newInstance()); } // new behavior as of 1.206 @@ -608,10 +609,8 @@ public T newInstance(@Nullable StaplerRequest req, @NonNull JSONObject formData) req.setBindInterceptor(oldInterceptor); } } - } catch (NoSuchMethodException e) { - throw new AssertionError(e); // impossible - } catch (InstantiationException | IllegalAccessException | RuntimeException e) { - throw new Error("Failed to instantiate "+clazz+" from "+RedactSecretJsonInErrorMessageSanitizer.INSTANCE.sanitize(formData),e); + } catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException | RuntimeException e) { + throw new LinkageError("Failed to instantiate "+clazz+" from "+RedactSecretJsonInErrorMessageSanitizer.INSTANCE.sanitize(formData),e); } } diff --git a/core/src/main/java/hudson/util/DescribableList.java b/core/src/main/java/hudson/util/DescribableList.java index ce2d08788f70..7aa11e88521c 100644 --- a/core/src/main/java/hudson/util/DescribableList.java +++ b/core/src/main/java/hudson/util/DescribableList.java @@ -31,6 +31,8 @@ import com.thoughtworks.xstream.io.HierarchicalStreamWriter; import com.thoughtworks.xstream.mapper.Mapper; import hudson.model.AbstractProject; +import java.io.UncheckedIOException; +import java.lang.reflect.InvocationTargetException; import jenkins.model.DependencyDeclarer; import hudson.model.DependencyGraph; import hudson.model.Describable; @@ -275,10 +277,14 @@ public void marshal(Object source, HierarchicalStreamWriter writer, MarshallingC @Override public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext context) { try { - DescribableList r = (DescribableList) context.getRequiredType().asSubclass(DescribableList.class).newInstance(); + DescribableList r = (DescribableList) context.getRequiredType().asSubclass(DescribableList.class).getDeclaredConstructor().newInstance(); CopyOnWriteList core = copyOnWriteListConverter.unmarshal(reader, context); r.data.replaceBy(core); return r; + } catch (NoSuchMethodException e) { + NoSuchMethodError x = new NoSuchMethodError(); + x.initCause(e); + throw x; } catch (InstantiationException e) { InstantiationError x = new InstantiationError(); x.initCause(e); @@ -287,6 +293,19 @@ public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext co IllegalAccessError x = new IllegalAccessError(); x.initCause(e); throw x; + } catch (InvocationTargetException e) { + Throwable t = e.getCause(); + if (t instanceof RuntimeException) { + throw (RuntimeException) t; + } else if (t instanceof IOException) { + throw new UncheckedIOException((IOException) t); + } else if (t instanceof Exception) { + throw new RuntimeException(t); + } else if (t instanceof Error) { + throw (Error) t; + } else { + throw new Error(e); + } } } } diff --git a/core/src/main/java/hudson/util/PersistedList.java b/core/src/main/java/hudson/util/PersistedList.java index 9268e195029f..50fcd1ced35c 100644 --- a/core/src/main/java/hudson/util/PersistedList.java +++ b/core/src/main/java/hudson/util/PersistedList.java @@ -35,6 +35,8 @@ import hudson.model.Saveable; import java.io.IOException; +import java.io.UncheckedIOException; +import java.lang.reflect.InvocationTargetException; import java.util.AbstractList; import java.util.ArrayList; import java.util.Arrays; @@ -287,9 +289,13 @@ public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext co CopyOnWriteList core = copyOnWriteListConverter.unmarshal(reader, context); try { - PersistedList r = (PersistedList)context.getRequiredType().newInstance(); + PersistedList r = (PersistedList)context.getRequiredType().getDeclaredConstructor().newInstance(); r.data.replaceBy(core); return r; + } catch (NoSuchMethodException e) { + NoSuchMethodError x = new NoSuchMethodError(); + x.initCause(e); + throw x; } catch (InstantiationException e) { InstantiationError x = new InstantiationError(); x.initCause(e); @@ -298,6 +304,19 @@ public Object unmarshal(HierarchicalStreamReader reader, UnmarshallingContext co IllegalAccessError x = new IllegalAccessError(); x.initCause(e); throw x; + } catch (InvocationTargetException e) { + Throwable t = e.getCause(); + if (t instanceof RuntimeException) { + throw (RuntimeException) t; + } else if (t instanceof IOException) { + throw new UncheckedIOException((IOException) t); + } else if (t instanceof Exception) { + throw new RuntimeException(t); + } else if (t instanceof Error) { + throw (Error) t; + } else { + throw new Error(e); + } } } } diff --git a/core/src/main/java/jenkins/ClassLoaderReflectionToolkit.java b/core/src/main/java/jenkins/ClassLoaderReflectionToolkit.java index 06a61b879b00..3992907a090c 100644 --- a/core/src/main/java/jenkins/ClassLoaderReflectionToolkit.java +++ b/core/src/main/java/jenkins/ClassLoaderReflectionToolkit.java @@ -31,7 +31,7 @@ private static Object invoke(Method method, Class excep try { return method.invoke(obj, args); } catch (IllegalAccessException x) { - throw new AssertionError(x); + throw new LinkageError(x.getMessage(), x); } catch (InvocationTargetException x) { Throwable x2 = x.getCause(); if (x2 instanceof RuntimeException) { @@ -193,7 +193,7 @@ public Class findLoadedClass(ClassLoader cl, String name) throws InvocationTarge try { return (Class)FindLoadedClass.FIND_LOADED_CLASS.invoke(cl,name); } catch (IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } @@ -203,7 +203,7 @@ public Class findClass(ClassLoader cl, String name) throws InvocationTargetExcep try { return (Class)FindClass.FIND_CLASS.invoke(cl,name); } catch (IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } @@ -213,7 +213,7 @@ public URL findResource(ClassLoader cl, String name) throws InvocationTargetExce try { return (URL)FindResource.FIND_RESOURCE.invoke(cl,name); } catch (IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } @@ -223,7 +223,7 @@ public Enumeration findResources(ClassLoader cl, String name) throws Invoca try { return (Enumeration)FindResources.FIND_RESOURCES.invoke(cl,name); } catch (IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } diff --git a/core/src/main/java/jenkins/model/lazy/LazyBuildMixIn.java b/core/src/main/java/jenkins/model/lazy/LazyBuildMixIn.java index 0aec9bc625b0..7215fbc86269 100644 --- a/core/src/main/java/jenkins/model/lazy/LazyBuildMixIn.java +++ b/core/src/main/java/jenkins/model/lazy/LazyBuildMixIn.java @@ -165,7 +165,7 @@ public RunT loadBuild(File dir) throws IOException { try { return getBuildClass().getConstructor(asJob().getClass(), File.class).newInstance(asJob(), dir); } catch (InstantiationException | NoSuchMethodException | IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } catch (InvocationTargetException e) { throw handleInvocationTargetException(e); } @@ -187,7 +187,7 @@ public final synchronized RunT newBuild() throws IOException { throw handleInvocationTargetException(e); } catch (ReflectiveOperationException | IllegalStateException e) { LOGGER.log(Level.WARNING, String.format("A new build could not be created in job %s", asJob().getFullName()), e); - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } diff --git a/core/src/main/java/jenkins/util/AntWithFindResourceClassLoader.java b/core/src/main/java/jenkins/util/AntWithFindResourceClassLoader.java index 58006e09fad7..4c03d41242e0 100644 --- a/core/src/main/java/jenkins/util/AntWithFindResourceClassLoader.java +++ b/core/src/main/java/jenkins/util/AntWithFindResourceClassLoader.java @@ -23,7 +23,7 @@ public AntWithFindResourceClassLoader(ClassLoader parent, boolean parentFirst) { $pathComponents.setAccessible(true); pathComponents = (ArrayList)$pathComponents.get(this); } catch (NoSuchFieldException | IllegalAccessException e) { - throw new Error(e); + throw new LinkageError(e.getMessage(), e); } } diff --git a/core/src/test/java/hudson/util/SubClassGeneratorTest.java b/core/src/test/java/hudson/util/SubClassGeneratorTest.java index d9ca838c63af..1cc590bb6dc6 100644 --- a/core/src/test/java/hudson/util/SubClassGeneratorTest.java +++ b/core/src/test/java/hudson/util/SubClassGeneratorTest.java @@ -49,7 +49,7 @@ public void foo() throws Exception { Class c = new SubClassGenerator(getClass().getClassLoader()).generate(Foo.class, "12345"); assertEquals("12345",c.getName()); - c.newInstance(); + c.getDeclaredConstructor().newInstance(); Foo f = c.getConstructor(String.class).newInstance("aaa"); assertEquals("aaa",f.s); diff --git a/test/src/test/java/hudson/tools/ZipExtractionInstallerTest.java b/test/src/test/java/hudson/tools/ZipExtractionInstallerTest.java index 3885d1e103ee..fe3b82c5c04c 100644 --- a/test/src/test/java/hudson/tools/ZipExtractionInstallerTest.java +++ b/test/src/test/java/hudson/tools/ZipExtractionInstallerTest.java @@ -160,7 +160,7 @@ public Object callFunction(HtmlPage page, Function function, Scriptable scope, S } } } catch (NoSuchFieldException | IllegalAccessException e) { - e.printStackTrace(); + throw new LinkageError(e.getMessage(), e); } } return super.callFunction(page, function, scope, thisObject, args);