You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tomee.apache.org by db...@apache.org on 2020/06/12 18:23:49 UTC
[tomee-patch-plugin] branch master updated: Fully functional
jar-patching and good log output
This is an automated email from the ASF dual-hosted git repository.
dblevins pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tomee-patch-plugin.git
The following commit(s) were added to refs/heads/master by this push:
new bff48fc Fully functional jar-patching and good log output
bff48fc is described below
commit bff48fc411e22a11840985859bfbe54246cf7886
Author: David Blevins <da...@gmail.com>
AuthorDate: Fri Jun 12 11:23:27 2020 -0700
Fully functional jar-patching and good log output
---
.../java/org/apache/tomee/patch/core/Clazz.java | 13 ++
.../apache/tomee/patch/core/Transformation.java | 168 +++++++++++++--------
.../{Clazz.java => UnappliedPatchesException.java} | 40 +----
.../org/apache/tomee/patch/plugin/PatchMojo.java | 1 +
4 files changed, 129 insertions(+), 93 deletions(-)
diff --git a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java
index 2c1a09e..e312a47 100644
--- a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java
+++ b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java
@@ -23,6 +23,7 @@ public class Clazz {
private final String name;
private final String prefix;
private final File file;
+ private int applied;
public Clazz(final String name, final File file) {
this.name = name;
@@ -30,6 +31,18 @@ public class Clazz {
this.file = file;
}
+ public void applied() {
+ this.applied++;
+ }
+
+ public boolean isApplied() {
+ return applied > 0;
+ }
+
+ public int getApplied() {
+ return applied;
+ }
+
public String getPrefix() {
return prefix;
}
diff --git a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Transformation.java b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Transformation.java
index 53bb1d8..09faa88 100644
--- a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Transformation.java
+++ b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Transformation.java
@@ -30,11 +30,13 @@ import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
-import java.util.concurrent.atomic.AtomicReference;
+import java.util.stream.Collectors;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;
import java.util.zip.ZipOutputStream;
+import static org.tomitribe.jkta.util.Predicates.not;
+
public class Transformation {
private final List<Clazz> classes = new ArrayList<Clazz>();
@@ -59,77 +61,76 @@ public class Transformation {
try (final InputStream inputStream = IO.read(jar)) {
try (final OutputStream outputStream = IO.write(tempFile)) {
- final Jar old = Jar.enter(jar.getName());
- try {
- scanJar(inputStream, outputStream);
- } finally {
- Jar.exit(old);
- }
- return tempFile;
+ scanJar(jar.getName(), inputStream, outputStream);
}
}
+
+ return tempFile;
}
- private void scanJar(final InputStream inputStream, final OutputStream outputStream) throws IOException {
- final ZipInputStream zipInputStream = new ZipInputStream(inputStream);
- final ZipOutputStream zipOutputStream = new ZipOutputStream(outputStream);
-
- ZipEntry oldEntry;
- while ((oldEntry = zipInputStream.getNextEntry()) != null) {
- // TODO: the name may be changed in transformation
- final String path = oldEntry.getName();
-
- /*
- * If this entry has been patched, skip it
- * We will add the patched version at the end
- */
- if (isPatched(path)) {
- log.debug("Skipping class " + path);
- IO.copy(zipInputStream, skipped);
- continue;
- }
+ private void scanJar(final String name, final InputStream inputStream, final OutputStream outputStream) throws IOException {
+ final Jar oldJar = Jar.enter(name);
+ final Jar jar = Jar.current();
+ try {
+ final ZipInputStream zipInputStream = new ZipInputStream(inputStream);
+ final ZipOutputStream zipOutputStream = new ZipOutputStream(outputStream);
+
+ ZipEntry oldEntry;
+ while ((oldEntry = zipInputStream.getNextEntry()) != null) {
+ // TODO: the name may be changed in transformation
+ final String path = oldEntry.getName();
+
+ /*
+ * If this entry has been patched, skip it
+ * We will add the patched version at the end
+ */
+ if (isPatched(path, jar)) {
+ log.debug("Skipping class " + path);
+ IO.copy(zipInputStream, skipped);
+ continue;
+ }
- final ZipEntry newEntry = new ZipEntry(path);
+ final ZipEntry newEntry = new ZipEntry(path);
-// copyAttributes(oldEntry, newEntry);
+ // copyAttributes(oldEntry, newEntry);
- zipOutputStream.putNextEntry(newEntry);
+ zipOutputStream.putNextEntry(newEntry);
- try {
- if (path.endsWith(".class")) {
- scanClass(zipInputStream, zipOutputStream);
- } else if (isZip(path)) {
- final Jar old = Jar.enter(path);
- try {
- scanJar(zipInputStream, zipOutputStream);
- } finally {
- Jar.exit(old); // restore the old state
+ try {
+ if (path.endsWith(".class")) {
+ scanClass(zipInputStream, zipOutputStream);
+ } else if (isZip(path)) {
+ scanJar(path, zipInputStream, zipOutputStream);
+ } else {
+ IO.copy(zipInputStream, zipOutputStream);
}
- } else {
- IO.copy(zipInputStream, zipOutputStream);
+ } finally {
+ zipOutputStream.closeEntry();
}
- } finally {
- zipOutputStream.closeEntry();
}
- }
- // If we skipped any classes, add them now
- if (Jar.current().hasPatches()) {
- log.info("Patching " + Jar.current().getName());
- for (final Clazz clazz : Jar.current().getSkipped()) {
- log.info("Applying patch " + clazz.getName());
+ // If we skipped any classes, add them now
+ if (jar.hasPatches()) {
+ log.info("Patching " + jar.getName());
+ for (final Clazz clazz : jar.getSkipped()) {
+ log.debug("Applying patch " + clazz.getName());
- final ZipEntry newEntry = new ZipEntry(clazz.getName());
- zipOutputStream.putNextEntry(newEntry);
+ final ZipEntry newEntry = new ZipEntry(clazz.getName());
+ zipOutputStream.putNextEntry(newEntry);
- // Run any transformations on these classes as well
- scanClass(IO.read(clazz.getFile()), zipOutputStream);
+ // Run any transformations on these classes as well
+ scanClass(IO.read(clazz.getFile()), zipOutputStream);
- zipOutputStream.closeEntry();
+ zipOutputStream.closeEntry();
+ clazz.applied();
+ }
}
+ zipOutputStream.finish();
+ } catch (IOException e) {
+ throw new IOException(jar.getPath() + e.getMessage(), e);
+ } finally {
+ Jar.exit(oldJar);
}
-
- zipOutputStream.close();
}
private static void copyAttributes(final ZipEntry oldEntry, final ZipEntry newEntry) {
@@ -156,20 +157,63 @@ public class Transformation {
outputStream.write(bytes);
}
+ public void complete() {
+ final List<Clazz> appliedPatches = classes.stream()
+ .filter(Clazz::isApplied)
+ .collect(Collectors.toList());
+
+ final List<Clazz> unappliedPatches = classes.stream()
+ .filter(not(Clazz::isApplied))
+ .collect(Collectors.toList());
+
+ final int applied = appliedPatches.stream()
+ .map(Clazz::getApplied)
+ .reduce(Integer::sum)
+ .orElse(0);
+
+ log.info(String.format("Applied %s patches to %s locations", appliedPatches.size(), applied));
+ appliedPatches.stream()
+ .map(Clazz::getName)
+ .map(s -> " " + s)
+ .forEach(log::debug);
+
+ if (unappliedPatches.size() > 0) {
+ final String message = String.format("Failed to apply %s patches", unappliedPatches.size());
+ log.error(message);
+ unappliedPatches.stream()
+ .map(Clazz::getName)
+ .map(s -> " " + s)
+ .forEach(log::error);
+ throw new UnappliedPatchesException(unappliedPatches);
+ }
+ }
+
public static class Jar {
- private static final AtomicReference<Jar> current = new AtomicReference<>(new Jar("<none>"));
+ private static final ThreadLocal<Jar> current = ThreadLocal.withInitial(Jar::new);
private final Set<Clazz> patches = new HashSet<>();
private final String name;
+ private final Jar parent;
+
+ private Jar() {
+ this.name = "";
+ this.parent = null;
+ }
- public Jar(final String name) {
+ private Jar(final String name, Jar parent) {
this.name = name;
+ this.parent = parent;
}
public String getName() {
return name;
}
+ public String getPath() {
+ if (parent == null) return name;
+ return parent.getPath() + "/" + name;
+ }
+
public boolean hasPatches() {
return patches.size() > 0;
}
@@ -179,11 +223,13 @@ public class Transformation {
}
public static Jar enter(final String name) {
- return current.getAndSet(new Jar(name));
+ final Jar old = current.get();
+ current.set(new Jar(name, old));
+ return old;
}
public static void exit(final Jar oldJar) {
- current.getAndSet(oldJar);
+ current.set(oldJar);
}
public Collection<Clazz> getSkipped() {
@@ -201,10 +247,10 @@ public class Transformation {
}
}
- private boolean isPatched(final String path) {
+ private boolean isPatched(final String path, final Jar jar) {
for (final Clazz clazz : classes) {
if (path.startsWith(clazz.getPrefix())) {
- Jar.current().patch(clazz, classes);
+ jar.patch(clazz, classes);
return true;
}
}
diff --git a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/UnappliedPatchesException.java
similarity index 51%
copy from tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java
copy to tomee-patch-core/src/main/java/org/apache/tomee/patch/core/UnappliedPatchesException.java
index 2c1a09e..68d9970 100644
--- a/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/Clazz.java
+++ b/tomee-patch-core/src/main/java/org/apache/tomee/patch/core/UnappliedPatchesException.java
@@ -16,42 +16,18 @@
*/
package org.apache.tomee.patch.core;
-import java.io.File;
-import java.util.Objects;
+import java.util.List;
-public class Clazz {
- private final String name;
- private final String prefix;
- private final File file;
+public class UnappliedPatchesException extends IllegalStateException {
- public Clazz(final String name, final File file) {
- this.name = name;
- this.prefix = name.replaceAll("\\.class$", "");
- this.file = file;
- }
-
- public String getPrefix() {
- return prefix;
- }
-
- public String getName() {
- return name;
- }
-
- public File getFile() {
- return file;
- }
+ private final List<Clazz> unappliedPatches;
- @Override
- public boolean equals(final Object o) {
- if (this == o) return true;
- if (o == null || getClass() != o.getClass()) return false;
- final Clazz clazz = (Clazz) o;
- return name.equals(clazz.name);
+ public UnappliedPatchesException(final List<Clazz> unappliedPatches) {
+ super(String.format("Failed to apply %s patches", unappliedPatches.size()));
+ this.unappliedPatches = unappliedPatches;
}
- @Override
- public int hashCode() {
- return Objects.hash(name);
+ public List<Clazz> getUnappliedPatches() {
+ return unappliedPatches;
}
}
diff --git a/tomee-patch-plugin/src/main/java/org/apache/tomee/patch/plugin/PatchMojo.java b/tomee-patch-plugin/src/main/java/org/apache/tomee/patch/plugin/PatchMojo.java
index e4e4ed8..a74eb2e 100644
--- a/tomee-patch-plugin/src/main/java/org/apache/tomee/patch/plugin/PatchMojo.java
+++ b/tomee-patch-plugin/src/main/java/org/apache/tomee/patch/plugin/PatchMojo.java
@@ -179,6 +179,7 @@ public class PatchMojo extends AbstractMojo {
IO.copy(patched, file);
}
+ transformation.complete();
} catch (IOException e) {
throw new MojoExecutionException("Error occurred during execution", e);
}