001 /*
002 Copyright (c) 1996-2012, Damon Hart-Davis
003 All rights reserved.
004
005 Redistribution and use in source and binary forms, with or without
006 modification, are permitted provided that the following conditions are
007 met:
008
009 * Redistributions of source code must retain the above copyright
010 notice, this list of conditions and the following disclaimer.
011
012 * Redistributions in binary form must reproduce the above copyright
013 notice, this list of conditions and the following disclaimer in the
014 documentation and/or other materials provided with the
015 distribution.
016
017 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
018 IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
019 TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
020 PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
021 OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
022 SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
023 LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
024 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
025 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
026 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
027 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
028 */
029 package org.hd.d.pg2k.svrCore;
030
031 import org.hd.d.pg2k.svrCore.vars.BasicVarMgrInterface;
032 import org.hd.d.pg2k.svrCore.vars.InstanceID;
033 import org.hd.d.pg2k.svrCore.vars.SimpleNumberStats;
034 import org.hd.d.pg2k.svrCore.vars.SimpleVarStats;
035 import org.hd.d.pg2k.svrCore.vars.SimpleVariableDefinition;
036 import org.hd.d.pg2k.svrCore.vars.SimpleVariableValue;
037 import org.hd.d.pg2k.svrCore.vars.SystemVariables;
038
039 /**This class has tools handling common SystemVariables.
040 */
041 public final class VarTools
042 {
043 /**Prevent creation of instances of this class. */
044 private VarTools() { }
045
046 /**Minimum age of globalMap entry we will discard, ms; strictly positive. */
047 public static final int MIN_AGE_MS = 2*SystemVariables.MAX_VALUE_DISTRIBUTION_LATENCY_MS;
048
049
050
051
052
053 /**Robustly computes simple stats on a named generic variable.
054 * The stats instance produced is
055 * @see #generateSimpleNumberStats
056 *
057 *
058 * @param maxAge_ms maximum age of globalMap entry we will use in ms;
059 * will be coerced upwards to a minimum value based on allowed
060 * variable-propagation latency
061 *
062 * Catches most exceptions and returns null in case of error.
063 * <p>
064 * Computes the system ID automatically, if available.
065 */
066 public static final SimpleVarStats generateSimpleStats(
067 final BasicVarMgrInterface dataSource,
068 final SimpleVariableDefinition def,
069 final int maxAge_ms)
070 {
071 if((dataSource == null) ||
072 (def == null))
073 { throw new IllegalArgumentException(); }
074
075 try
076 {
077 final SimpleVariableValue sys =
078 dataSource.getVariable(SystemVariables.LOCAL_SYS_ID);
079 // Build and return the requested stats...
080 return(new SimpleVarStats(dataSource.getVariable(def),
081 System.currentTimeMillis() -
082 Math.max(maxAge_ms, MIN_AGE_MS),
083 (sys == null) ? null : (InstanceID) sys.getValue()));
084 }
085 catch(final Exception e)
086 { return(null); }
087 }
088
089 /**Robustly computes simple stats on a named TYPE_NUMBER variable.
090 * @see #generateSimpleNumberStats
091 *
092 * @param maxAge_ms maximum age of globalMap entry we will use in ms;
093 * will be coerced upwards to a minimum value based on allowed
094 * variable-propagation latency
095 *
096 * Catches most exceptions and returns null in case of error.
097 * <p>
098 * Computes the system ID automatically, if available.
099 */
100 public static final SimpleNumberStats generateSimpleNumberStats(
101 final BasicVarMgrInterface dataSource,
102 final SimpleVariableDefinition def,
103 final int maxAge_ms,
104 final String decimalFormatPattern)
105 {
106 if((dataSource == null) ||
107 (def == null))
108 { throw new IllegalArgumentException(); }
109
110 try
111 {
112 final SimpleVariableValue sys =
113 dataSource.getVariable(SystemVariables.LOCAL_SYS_ID);
114 return(generateSimpleNumberStats(dataSource.getVariable(def),
115 maxAge_ms,
116 decimalFormatPattern,
117 (sys == null) ? null : (InstanceID) sys.getValue()));
118 }
119 catch(final Exception e)
120 { return(null); }
121 }
122
123
124 /**Robustly computes simple stats on a TYPE_NUMBER variable.
125 * Intended to be used both in normal code and
126 * directly in JSP pages
127 * (eg is robust, never throws exceptions, HMTL-friendly toString()).
128 * <p>
129 * Returns an immutable object containing the stats
130 * which has a toString() which renders a relatively
131 * admin-human-friendly simple String containing all the stats,
132 * or null if the variable presented is null or not numeric
133 * or for some reason not suitable.
134 * <p>
135 * A local value is treated like a global with one entry
136 * but flagged as local.
137 * <p>
138 * Only the young-enough members of a global are used;
139 * if none are young enough then the main value is used
140 * and flagged as old.
141 *
142 * @param sysID identifies this system so we can select the local
143 * value of a global variable if available; can be null
144 * @param maxAge maximum age of globalMap entries to be used;
145 * coerced to be at least a little larger than the refresh
146 *
147 * @return null if variable is unsuitable, else encapsulated stats
148 */
149 public static final SimpleNumberStats generateSimpleNumberStats(
150 final SimpleVariableValue var,
151 final int maxAge,
152 final String decimalFormatPattern,
153 final InstanceID sysID)
154 {
155 // Return null if the variable is unsuitable.
156 if((var == null) ||
157 (var.getDef().getType() != SimpleVariableDefinition.TYPE_NUMBER) ||
158 (var.getValue() == null))
159 { return(null); }
160
161 // Build and return the requested stats...
162 return(new SimpleNumberStats(var,
163 System.currentTimeMillis() -
164 Math.max(maxAge, MIN_AGE_MS),
165 sysID, decimalFormatPattern
166 ));
167 }
168 }