This is an automated email from the ASF dual-hosted git repository.
rmaucher pushed a commit to branch 9.0.x
in repository https://gitbox.apache.org/repos/asf/tomcat.git
The following commit(s) were added to refs/heads/9.0.x by this push:
new 77cdcdcc54 Fix container cleanup edge cases
77cdcdcc54 is described below
commit 77cdcdcc54d0001941ffdf4cf00cdeef72fcafca
Author: remm <[email protected]>
AuthorDate: Thu May 21 10:56:42 2026 +0200
Fix container cleanup edge cases
The remove event should be sent if the child container is actually
removed, not based on some other factor.
The framework listener should self clean a bit more when removing a
container. Normally the children would be removed first, but doing this
does not hurt.
---
java/org/apache/catalina/core/ContainerBase.java | 13 ++++++-------
java/org/apache/catalina/core/FrameworkListener.java | 4 ++++
webapps/docs/changelog.xml | 3 +++
3 files changed, 13 insertions(+), 7 deletions(-)
diff --git a/java/org/apache/catalina/core/ContainerBase.java
b/java/org/apache/catalina/core/ContainerBase.java
index acc3178807..ae15831391 100644
--- a/java/org/apache/catalina/core/ContainerBase.java
+++ b/java/org/apache/catalina/core/ContainerBase.java
@@ -679,30 +679,29 @@ public abstract class ContainerBase extends
LifecycleMBeanBase implements Contai
log.error(sm.getString("containerBase.child.stop"), e);
}
- boolean destroy = false;
try {
// child.destroy() may have already been called which would have
// triggered this call. If that is the case, no need to destroy the
// child again.
if (!LifecycleState.DESTROYING.equals(child.getState())) {
child.destroy();
- destroy = true;
}
} catch (LifecycleException e) {
log.error(sm.getString("containerBase.child.destroy"), e);
}
- if (!destroy) {
- fireContainerEvent(REMOVE_CHILD_EVENT, child);
- }
-
+ boolean removed = false;
childrenLock.writeLock().lock();
try {
- children.remove(child.getName());
+ removed = children.remove(child.getName()) != null;
} finally {
childrenLock.writeLock().unlock();
}
+ if (removed) {
+ fireContainerEvent(REMOVE_CHILD_EVENT, child);
+ }
+
}
diff --git a/java/org/apache/catalina/core/FrameworkListener.java
b/java/org/apache/catalina/core/FrameworkListener.java
index 5ea43c5ca0..3742ad6a16 100644
--- a/java/org/apache/catalina/core/FrameworkListener.java
+++ b/java/org/apache/catalina/core/FrameworkListener.java
@@ -154,6 +154,10 @@ public abstract class FrameworkListener implements
LifecycleListener, ContainerL
}
} else if (child instanceof Host || child instanceof Engine) {
child.removeContainerListener(this);
+ Container[] children = child.findChildren();
+ for (Container current : children) {
+ processContainerRemoveChild(current);
+ }
}
}
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index 07e4a5efd7..180fdce725 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -141,6 +141,9 @@
similar to what is done for servlets, as required by the servlet
specification. (remm)
</fix>
+ <fix>
+ Fix container event cleanups in some edge cases. (remm)
+ </fix>
</changelog>
</subsection>
<subsection name="Coyote">
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]