use of net.sourceforge.processdash.data.compiler.CompiledScript in project processdash by dtuma.
the class RollupAutoData method buildRollupData.
private void buildRollupData(DataRepository data) {
//System.out.println("buildRollupData for " + definesRollupID);
Map baseDefinitions = null;
try {
baseDefinitions = data.loadIncludedFileDefinitions(basedOnDataFile);
// can exit immediately.
if (definitions != null)
return;
} catch (Exception e) {
logger.log(Level.WARNING, "Caught Exception", e);
return;
}
Map rollupDefinitions = new HashMap();
StringBuffer definitionBuffer = new StringBuffer();
definitionBuffer.append("#define ROLLUP_ID ").append(esc(definesRollupID));
// Define macros for rolling up numbers and lists
definitionBuffer.append("\n#define ROLLUP_NUMBER(Data) ");
rollupDouble(definitionBuffer, "Data");
definitionBuffer.append("\n#define ROLLUP_LIST(Data) ");
rollupList(definitionBuffer, "Data");
// Include the standard rollup data definitions
definitionBuffer.append("\n").append(ROLLUP_DATA).append("\n");
Map toDateAliasDefinitions = new HashMap();
String toDatePrefix = "/To Date/" + definesRollupID + "/All";
toDateAliasDefinitions.put(definesRollupID + " To Date Subset Prefix", StringData.create(toDatePrefix));
StringBuffer toDateAliasBuffer = new StringBuffer();
Iterator i = baseDefinitions.entrySet().iterator();
Map.Entry definition;
String name;
Object value;
while (i.hasNext()) {
definition = (Map.Entry) i.next();
name = (String) definition.getKey();
value = definition.getValue();
if (skipElement(name, value))
// filter out elements which should not be rolled up.
continue;
else if (value instanceof DoubleData) {
// roll up the values of any literal double data elements.
rollupDouble(definitionBuffer, name);
addAlias(toDateAliasBuffer, name, definesRollupID);
} else if (value instanceof ListFunction)
// roll up the values of any search()-generated lists.
rollupList(definitionBuffer, name);
else if (value != null) {
if (value instanceof CompiledScript)
addAlias(toDateAliasBuffer, name, definesRollupID);
// DO NOT roll up dates, strings, lists, tags,
// compiled functions, or old-style definitions - just
// copy them into the rollup set verbatim.
rollupDefinitions.put(name, value);
}
}
// Calculate the rollup aliases
parseDefinitions(data, toDateAliasBuffer.toString(), toDateAliasDefinitions);
aliasDefs = toDateAliasDefinitions;
// If the user specified a datafile for this rollup, include it.
if (XMLUtils.hasValue(rollupDataFile))
try {
URLConnection conn = TemplateLoader.resolveURLConnection(rollupDataFile);
String contents = new String(FileUtils.slurpContents(conn.getInputStream(), true));
definitionBuffer.append("\n").append(contents).append("\n");
} catch (IOException ioe) {
logger.log(Level.WARNING, "IOException", ioe);
}
// Calculate the rollup definitions and return them.
parseDefinitions(data, definitionBuffer.toString(), rollupDefinitions);
definitions = rollupDefinitions;
debugPrint(rollupDefinitions);
try {
// Mount this rollup data set in the repository.
data.mountPhantomData(toDatePrefix, rollupDefinitions);
} catch (Exception e) {
logger.log(Level.WARNING, "Caught Exception", e);
}
}
use of net.sourceforge.processdash.data.compiler.CompiledScript in project processdash by dtuma.
the class DataRepository method instantiateValue.
private SaveableData instantiateValue(String name, String dataPrefix, Object valueObj, boolean readOnly) {
SaveableData o = null;
if (valueObj instanceof SimpleData) {
o = (SimpleData) valueObj;
if (readOnly)
o = o.getEditable(false);
} else if (valueObj instanceof CompiledScript) {
o = new CompiledFunction(name, (CompiledScript) valueObj, this, dataPrefix);
} else if (valueObj instanceof SearchFactory) {
o = ((SearchFactory) valueObj).buildFor(name, this, dataPrefix);
} else if (valueObj instanceof String) {
String value = (String) valueObj;
if (value.startsWith("=")) {
readOnly = true;
value = value.substring(1);
}
try {
o = ValueFactory.createQuickly(name, value, this, dataPrefix);
} catch (MalformedValueException mfe) {
// temporary fix to allow old PSP for Engineers add-on to work in 1.7
if ("![(&&\tCompleted)]".equals(value)) {
valueObj = Compiler.compile("[Completed]");
o = new CompiledFunction(name, (CompiledScript) valueObj, this, dataPrefix);
} else {
o = new MalformedData(value);
}
}
if (readOnly && o != null)
o.setEditable(false);
}
return o;
}
use of net.sourceforge.processdash.data.compiler.CompiledScript in project processdash by dtuma.
the class DataRepository method mountData.
void mountData(DataFile dataFile, String dataPrefix, Map values) throws InvalidDatafileFormat {
try {
startInconsistency();
boolean registerDataNames = false;
String datafilePath = "internal data";
boolean fileEditable = true;
// if this is a regular file,
if (dataFile != null && dataFile.file != null) {
datafilePath = dataFile.file.getPath();
fileEditable = dataFile.canWrite && Settings.isReadWrite();
// register the names of data elements in this file IF it is
// not global data.
registerDataNames = dataPrefix.length() > 0;
}
Map defaultData = dataFile.inheritedDefinitions;
if (defaultData == null)
defaultData = Collections.EMPTY_MAP;
boolean successful = false;
boolean datafileModified = false;
int retryCount = 10;
while (!successful && retryCount-- > 0) try {
// values map.
for (Iterator i = values.entrySet().iterator(); i.hasNext(); ) {
Map.Entry defn = (Map.Entry) i.next();
String localName = (String) defn.getKey();
Object valueObj = defn.getValue();
String dataName = createDataName(dataPrefix, localName);
SaveableData o = instantiateValue(dataName, dataPrefix, valueObj, !fileEditable);
if (o instanceof MalformedData)
logger.warning("Data value for '" + dataName + "' in file '" + datafilePath + "' is malformed.");
DataElement d = (DataElement) data.get(dataName);
if (d == null) {
boolean isDefaultName = defaultData.containsKey(localName);
if (o != null || isDefaultName) {
try {
add(dataName, isDefaultName, o, IS_NOT_DEFAULT_VAL, dataFile, DO_NOTIFY);
} catch (DataElementAlreadyExistsException e) {
d = e.elem;
}
}
}
if (d != null) {
putValue(dataName, o, IS_NOT_DEFAULT_VAL, NOT_MODIFYING_DATAFILE);
d = (DataElement) data.get(dataName);
if (d != null) {
d.datafile = dataFile;
d.isDefaultName = defaultData.containsKey(localName);
}
}
if (registerDataNames && (o instanceof DoubleData || o instanceof CompiledFunction))
dataElementNameSet.add(localName);
}
// Next, handle the default values that this datafile inherits.
String dataPrefixSlash = dataPrefix + "/";
for (Iterator i = defaultData.entrySet().iterator(); i.hasNext(); ) {
Map.Entry defn = (Map.Entry) i.next();
String localName = (String) defn.getKey();
Object valueObj = defn.getValue();
// name, do nothing.
if (values.containsKey(localName))
continue;
// Ignore renaming operations; they are not relevant.
if (valueObj instanceof DataRenamingOperation)
continue;
boolean shouldCreateEagerly = shouldCreateEagerly(valueObj);
if ("@now".equals(valueObj))
shouldCreateEagerly = datafileModified = true;
String dataName = dataPrefixSlash + localName;
DataElement d = (DataElement) data.get(dataName);
if (d == null) {
if (shouldCreateEagerly) {
// the item doesn't exist, but we should create it anyway.
SaveableData o = instantiateValue(dataName, dataPrefix, valueObj, !fileEditable);
if (o != null) {
try {
add(dataName, IS_DEFAULT_NAME, o, IS_DEFAULT_VAL, dataFile, DO_NOT_NOTIFY);
} catch (DataElementAlreadyExistsException e) {
d = e.elem;
}
}
}
}
if (d != null) {
// a matching data element exists.
d.datafile = dataFile;
d.isDefaultName = true;
dataName = d.name;
if (instantiatedDataMatches(valueObj, d.getValue())) {
// the data element already has the proper value. (This
// will be common, as clients registering data listeners
// will cause lazy data to spring to life even as this
// for loop is executing.) Nothing needs to be done.
} else if (!d.hasListeners()) {
// This element has the wrong value, but no one is
// listening to it. Revert the element to a lazy
// default value.
janitor.cleanup(d);
} else {
// This element has the wrong value, and clients are
// listening to it. Create and save the correct value.
SaveableData o = instantiateValue(dataName, dataPrefix, valueObj, !fileEditable);
putValue(dataName, o, IS_DEFAULT_VAL, NOT_MODIFYING_DATAFILE);
}
}
// send an event stating that the element is added. (Elsewhere in
// DataRepository, added events are never sent for data elements
// with default names (because it cannot tell whether the item is
// springing forth for the first time, or a subsequent time).
repositoryListenerList.dispatchAdded(dataName);
if (registerDataNames && (valueObj instanceof DoubleData || valueObj instanceof CompiledScript))
dataElementNameSet.add(localName);
}
// make a call to getID. We don't need the resulting value, but
// having made the call will cause an ID to be mapped for this
// prefix. This is necessary to allow users to bring up HTML pages
// from their browser's history or bookmark list.
getID(dataPrefix);
if (defaultData == globalDataDefinitions)
globalDataIsMounted = true;
if (datafileModified)
datafileModified(dataFile);
successful = true;
} catch (Throwable e) {
if (retryCount > 0) {
// Try again to open this datafile. Most errors are transient,
// caused by incredibly infrequent thread-related problems.
logger.log(Level.WARNING, "when opening " + datafilePath + " caught error; retrying.", e);
} else {
// We've done our best, but after 10 tries, we still can't open
// this datafile. Give up and throw an exception.
dataFile.invalidate();
closeDatafile(dataPrefix);
throw new InvalidDatafileFormat("Caught unexpected exception " + e);
}
}
} finally {
finishInconsistency();
}
}
use of net.sourceforge.processdash.data.compiler.CompiledScript in project processdash by dtuma.
the class DataNameCollector method run.
public static Collection run(DataRepository data, String prefix, boolean numbersOnly, boolean discardHidden, Collection dest) {
Map dataElements = data.getDefaultDataElementsFor(prefix);
if (dataElements == null)
return dest;
Pattern hiddenDataPattern = null;
if (discardHidden)
try {
String hiddenRegexp = "(" + Settings.getVal(SETTING_NAME) + ")";
hiddenDataPattern = Pattern.compile(hiddenRegexp, Pattern.CASE_INSENSITIVE);
} catch (Exception e) {
}
for (Iterator i = dataElements.entrySet().iterator(); i.hasNext(); ) {
Map.Entry e = (Map.Entry) i.next();
String name = (String) e.getKey();
if (numbersOnly) {
Object val = e.getValue();
if ((val instanceof DoubleData == false) && (val instanceof CompiledScript == false))
continue;
if (NONNUMERIC_DATA.contains(name))
continue;
}
if (hiddenDataPattern != null && hiddenDataPattern.matcher(name).find())
continue;
dest.add(name);
}
return dest;
}
Aggregations