Я реализовал эту функциональность с помощью общего подхода с использованием стандартных API и спецификаций, сторонних фреймворков или библиотек. Это решение широко использовалось во многих системах корпоративного уровня, развернутых на сервере приложений и jboss на стеклянных досках. Он также успешно используется с weblogic (12c). Тем не менее, этот подход должен работать в любом сервере приложений или сервлете, поддерживающем стандартную спецификацию JMX.
tldr; - это создание двух интерфейсов компонента JMX и одного прослушивателя сеанса http. Один из интерфейсов компонента JMX создает один экземпляр для каждого контролируемого приложения и отвечает за отслеживание всех сеансов от каждого контролируемого приложения, он в основном обеспечивает статистику всех сеансов для каждого приложения. Другой интерфейс компонента JMX создает один экземпляр для каждого сеанса, созданного в каждом контролируемом приложении. Слушатель сеанса http отслеживает сеансы каждого приложения и выполняет две функции. Сообщает о первом компоненте JMX, соответствующем этому приложению, о сеансах, созданных/уничтоженных, для обновления статистики. Регистрирует или деблокирует экземпляры JMX, соответствующие сеансу, из службы JMX.
Как только все будет установлено, его можно использовать с помощью JMX-клиента, такого как jconsole и visualvm, который поставляется вместе с jdk. Из jmx-клиента можно просмотреть все свойства компонентов JMX, а также вызвать любой из их методов.
Следующие скриншоты из тестового приложения, использующего jconsole.
Эти атрибуты из экземпляра компонента JMX, соответствующего каждому приложению контролируемого.
Эти операции, которые могут быть выполнены на конкретной сессии, выбранной.
Если отслеживается несколько приложений, тогда будет присутствовать больше контекстов приложения со своими собственными структурами, то есть/TestApplication,/Application2 и т. Д. Под каждым из интерфейсов bean-компонента jmx.
КАК
Первоначально необходимо создать два JMX боба интерфейса (simple tutorial), а затем один HttpSessionListener (много учебников онлайн).
1. В первом интерфейсе компонента JMX будет отображаться только один экземпляр для каждого приложения и будет хранить всю информацию, связанную с сеансами, созданными из любого из контролируемых приложений. Он в основном используется для настойчивости. Я сохраняю данные только в памяти, а это означает, что данные будут потеряны, если сервер опустится, но обычно требуется проверять статистику до тех пор, пока сервер не работает. Если вы хотите сохранить данные в журнале или db, чтобы всегда иметь эту информацию, вы можете сделать это в рамках реализации интерфейса.
Так что это может быть следующим,
public interface SessionsMXBean {
/**
* Get Indicates whether the data should be persisted in memory.
*/
public boolean getPersistData();
/**
* Set Indicates whether the data should be persisted in memory.
*/
public void setPersistData(boolean value);
/**
* Get All active sessions that have been persisted.
*/
public String getActiveSessions();
/**
* Get All dates of each active session that has been persisted.
*/
public String getDatesOfSessions();
/**
* Get The threshold for the number of session, after which persistence will
* take place. If -1 all are persisted.
*/
public int getSessionsThreshold();
/**
* Set The threshold for the number of session, after which persistence will
* take place. If -1 all are persisted.
*/
public void setSessionsThreshold(int value);
/**
* Set The limit of size to be persisted in KB. If -1 then no size limit.
*/
public void setPersistenceSize(long value);
/**
* Clears all persisted data.
*/
public void clearData();
/**
* Unregisters this instance
*/
public void unregisterThis();
}
Затем вы должны создать реализацию этого интерфейса, который будет в конечном итоге провести такого рода данных.
public class SessionsImpl implements SessionsMXBean {
/*
here you need to implement the interface and have all kind of objects you require
*/
public synchronized void incrementSessions() {
....
}
public synchronized void decrementSessions() {
.....
}
2. второй JMX интерфейс боб будет иметь один экземпляр для каждого сеанса, созданного в каждом из ваших отслеживаемых приложений. Этот интерфейс будет хранить объект сеанса и также будет иметь методы, которые могут быть вызваны из клиента jmx, чтобы аннулировать эти сеансы. Это может быть следующим,
public interface HttpSessionMXBean {
/**
* Get HTTP Session id
*/
public String getSessionId();
/**
* Get the date created
*/
public String getDateCreated();
/**
* Get the date created in milliseconds
*/
public long getMillisCreated();
/**
* Get attributes from http session
*
* @param attrName Attribute Name
* @return java.lang.String
*/
public String getAttribute(String attrName);
/**
* Invalidate this session
*/
public void invalidate();
/**
* Unregisters this instance
*/
public void unregisterThis();
}
И снова требуется реализация,
public class HttpSessionMXBeanImpl implements HttpSessionMXBean {
....
3.Then вы создаете HttpSessionListener, который будет создавать/удалять экземпляры 2-го интерфейса боба и регистрации/Unregister их из службы JMX вашего сервера. Это произойдет, когда сеансы создаются и аннулируются/истек. Таким образом, у вас будет один прослушиватель для каждого приложения, которое определено в его web.xml.
HttpSessionListener
....
public class MyJMXHTTPSessionListener implements HttpSessionListener {
....
private SessionsImpl sesssionsImpl;
private Map<String, HttpSessionMXBeanImpl> httpSessionMXBeans
@Override
public void sessionCreated(HttpSessionEvent se) {
//requires synchronized block here with this i.e.
synchronized (this) {
/*check if a jmx bean instance of the 1st interface exists otherwise create one*/
if(sessionsImpl==null){
sesssionsImpl= new SesssionsImpl();
/* take care here to create a nice and unique path per instance
of the application in order to be nicely presented on the JMX tree of the JMX clients */
String id = ("services.jmx.beans:type=Sessions,"+ "realm=" + se.getSession().getServletContext().getContextPath());
sessionManagerMXBean.setId(id);
ObjectName objectName = new ObjectName(id);
if (ManagementFactory.getPlatformMBeanServer().isRegistered(objectName)) {
ManagementFactory.getPlatformMBeanServer().
unregisterMBean(objectName);
}
ManagementFactory.getPlatformMBeanServer().
registerMBean(sesssionsImpl,
objectName);
}
sesssionsImpl.inrementSessions();
/*
create a jmx bean instance of the 2nd interface
and register it to the jmx service as already shown using the unique session id
and a nice path indicating the 2nd interface jmx beans.
*/
}
@Override
public void sessionDestroyed(HttpSessionEvent se) {
//requires synchronized block here with this i.e.
synchronized (this) {
/*unregister the jmx bean instance of the 2nd interface,
remove it from the list
and call decrementSessions() on the jmx bean instance corresponding to this app*/
}
}
}
Эта функциональность может быть легко активирован в любое время для любого веб-приложения, если определить HttpSessionListener в файле web.xml, добавив следующие несколько строк,
web.xml
<listener>
<listener-class>
myservices.myhttpsessionlisteners.MyJMXHTTPSessionListener
</listener-class>
</listener>
Похоже, что tomcat предоставляет средства мониторинга через JMX. Посмотрите http://tomcat.apache.org/tomcat-6.0-doc/monitoring.html – Karthik