/* * ALMA - Atacama Large Millimiter Array (c) European Southern Observatory, 2010 * * This library is free software; you can redistribute it and/or modify it under * the terms of the GNU Lesser General Public License as published by the Free * Software Foundation; either version 2.1 of the License, or (at your option) * any later version. * * This library is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more * details. * * You should have received a copy of the GNU Lesser General Public License * along with this library; if not, write to the Free Software Foundation, Inc., * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * */ package alma.acs.alarmsystemprofiler.document; import java.sql.Timestamp; import java.util.Calendar; import java.util.Collection; import java.util.Date; import java.util.concurrent.ConcurrentHashMap; import org.eclipse.jface.viewers.TableViewer; import alma.acs.alarmsystemprofiler.engine.AlarmUtils; import alma.acs.alarmsystemprofiler.save.TableData; import alma.alarmsystem.clients.source.SourceListener; import cern.laser.source.alarmsysteminterface.FaultState; /** * A class for stale alarms i.e. alarms activated and never deactivated. * <P> * Active alarms are stored in a map. When a <code>TERMINATE</code> alarms arrive and the alarm is in the map, it is removed. * If an alarm already present in the map is activated again, it is not modified because we are interested in the longest * time interval. * * @author acaproni * */ public class StaleAlarmsContainer extends DocumentBase implements SourceListener { /** * A stale alarm. * <P> * {@link Comparable} orders by activation time. * * @author acaproni * */ public class StaleAlarm implements Comparable<StaleAlarm> { /** * The ID of the alarm */ public final String ID; /** * The time when the alarm has been activated */ public final Timestamp activationTime; /** * Constructor * * @param id The ID of the alarm * @param time The time when the alarm has been activated */ public StaleAlarm(String id, Timestamp time) { this.ID=id; this.activationTime=time; } /** * Return a string with the time that the alarm is active * * @return How long the alarm is active */ public String activationDuration() { Calendar cal=Calendar.getInstance(); long now =cal.getTime().getTime(); long alTime=activationTime.getTime(); cal.setTime(new Date(now-alTime)); int days = cal.get(Calendar.DAY_OF_YEAR)-1; int hrs = cal.get(Calendar.HOUR_OF_DAY); int mins = cal.get(Calendar.MINUTE); int secs = cal.get(Calendar.SECOND); if (days<=0) { return String.format("%02d:%02d:%02d", hrs,mins,secs); } else { return String.format("%d days, %02d:%02d:%02d", days,hrs,mins,secs); } } @Override public int compareTo(StaleAlarm o) { if (o==null) { throw new NullPointerException(); } return activationTime.compareTo(o.activationTime); } } /** * The singleton */ private static StaleAlarmsContainer singleton=null; public static StaleAlarmsContainer getInstance() { if (singleton==null) { singleton = new StaleAlarmsContainer(); } return singleton; } /** * Constructor */ private StaleAlarmsContainer() { super("Stale alarms", new String[] { "Alarm ID", "active since" }); } /** * The stale alarms in staleAlarms are active alarms. * <P> * When a <code>TERMINATE</code> alarms is received, and an active alarm is in this list then it must be removed. * <P> * The key is the ID of the alarm. */ private final ConcurrentHashMap<String, StaleAlarm> staleAlarms = new ConcurrentHashMap<String, StaleAlarm>(); @Override public void faultStateReceived(FaultState faultState) { if (faultState==null || shutdown) { return; } String ID=AlarmUtils.getID(faultState); if (faultState.getDescriptor().equals(FaultState.ACTIVE)) { if (staleAlarms.containsKey(ID)) { return; } StaleAlarm alarm = new StaleAlarm(ID, faultState.getUserTimestamp()); staleAlarms.put(ID, alarm); } else if (faultState.getDescriptor().equals(FaultState.TERMINATE)) { if (!staleAlarms.containsKey(ID)) { return; } staleAlarms.remove(ID); } else { System.out.println("Unknown "+ID+"state "+faultState.getDescriptor()); } } @Override public void sourceXMLMsgReceived(String asiMessage) {} /** * * @return All the alarms in the container */ public Collection<StaleAlarm> getNumbers() { return staleAlarms.values(); } /** * Ovveride to start the thread to refresh the vie */ @Override public void setTableViewer(TableViewer table) { super.setTableViewer(table); Thread t = new Thread(this,this.getClass().getName()); t.setDaemon(true); t.start(); } @Override public void setTableContent(TableData tData) { Collection<StaleAlarm> vals = staleAlarms.values(); for (StaleAlarm val: vals) { String[] row = new String[2]; row[0]="="+val.ID+"="; row[1]=val.activationDuration(); tData.addRowData(row); } } }