fable 3.1.53 → 3.1.55
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/fable.js +43 -34
- package/dist/fable.js.map +1 -1
- package/dist/fable.min.js +2 -2
- package/dist/fable.min.js.map +1 -1
- package/docs/index.html +36 -48
- package/package.json +5 -5
- package/source/services/Fable-Service-ExpressionParser/Fable-Service-ExpressionParser-FunctionMap.json +5 -0
- package/source/services/Fable-Service-Utility.js +12 -0
- package/test/ExpressionParser_tests.js +4 -0
package/dist/fable.js
CHANGED
|
@@ -667,7 +667,7 @@ switch(pLevel){case'trace':this.logStreamsTrace.push(pLogger);case'debug':this.l
|
|
|
667
667
|
for(let i=0;i<this._StreamDefinitions.length;i++){let tmpStreamDefinition=Object.assign({loggertype:'default',streamtype:'console',level:'info'},this._StreamDefinitions[i]);if(!(tmpStreamDefinition.loggertype in this._Providers)){console.log(`Error initializing log stream: bad loggertype in stream definition ${JSON.stringify(tmpStreamDefinition)}`);}else{this.addLogger(new this._Providers[tmpStreamDefinition.loggertype](tmpStreamDefinition,this),tmpStreamDefinition.level);}}// Now initialize each one.
|
|
668
668
|
for(let i=0;i<this.logStreams.length;i++){this.logStreams[i].initialize();}}logTime(pMessage,pDatum){let tmpMessage=typeof pMessage!=='undefined'?pMessage:'Time';let tmpTime=new Date();this.info(`${tmpMessage} ${tmpTime} (epoch ${+tmpTime})`,pDatum);}// Get a timestamp
|
|
669
669
|
getTimeStamp(){return+new Date();}getTimeDelta(pTimeStamp){let tmpEndTime=+new Date();return tmpEndTime-pTimeStamp;}// Log the delta between a timestamp, and now with a message
|
|
670
|
-
logTimeDelta(pTimeDelta,pMessage,pDatum){let tmpMessage=typeof pMessage!=='undefined'?pMessage:'Time Measurement';let tmpDatum=typeof pDatum==='object'?pDatum:{};let tmpEndTime=+new Date();this.info(`${tmpMessage} logged at (epoch ${+tmpEndTime}) took (${pTimeDelta}ms)`,pDatum);}logTimeDeltaHuman(pTimeDelta,pMessage,pDatum){let tmpMessage=typeof pMessage!=='undefined'?pMessage:'Time Measurement';let tmpEndTime=+new Date();let tmpMs=parseInt(pTimeDelta%1000);let tmpSeconds=parseInt(pTimeDelta/1000%60);let tmpMinutes=parseInt(pTimeDelta/(1000*60)%60);let tmpHours=parseInt(pTimeDelta/(1000*60*60));tmpMs=tmpMs<10?"00"+tmpMs:tmpMs<100?"0"+tmpMs:tmpMs;tmpSeconds=tmpSeconds<10?"0"+tmpSeconds:tmpSeconds;tmpMinutes=tmpMinutes<10?"0"+tmpMinutes:tmpMinutes;tmpHours=tmpHours<10?"0"+tmpHours:tmpHours;this.info(`${tmpMessage} logged at (epoch ${+tmpEndTime}) took (${pTimeDelta}ms) or (${tmpHours}:${tmpMinutes}:${tmpSeconds}.${tmpMs})`,pDatum);}logTimeDeltaRelative(pStartTime,pMessage,pDatum){this.logTimeDelta(this.getTimeDelta(pStartTime),pMessage,pDatum);}logTimeDeltaRelativeHuman(pStartTime,pMessage,pDatum){this.logTimeDeltaHuman(this.getTimeDelta(pStartTime),pMessage,pDatum);}}module.exports=FableLog;module.exports.LogProviderBase=require('./Fable-Log-BaseLogger.js');module.exports.LogProviderConsole=require('./Fable-Log-Logger-Console.js');module.exports.LogProviderFlatfile=require('./Fable-Log-Logger-SimpleFlatFile.js');},{"../package.json":51,"./Fable-Log-BaseLogger.js":52,"./Fable-Log-DefaultProviders-Node.js":53,"./Fable-Log-DefaultStreams.json":54,"./Fable-Log-Logger-Console.js":55,"./Fable-Log-Logger-SimpleFlatFile.js":56,"fable-serviceproviderbase":59}],58:[function(require,module,exports){module.exports={"name":"fable-serviceproviderbase","version":"3.0.
|
|
670
|
+
logTimeDelta(pTimeDelta,pMessage,pDatum){let tmpMessage=typeof pMessage!=='undefined'?pMessage:'Time Measurement';let tmpDatum=typeof pDatum==='object'?pDatum:{};let tmpEndTime=+new Date();this.info(`${tmpMessage} logged at (epoch ${+tmpEndTime}) took (${pTimeDelta}ms)`,pDatum);}logTimeDeltaHuman(pTimeDelta,pMessage,pDatum){let tmpMessage=typeof pMessage!=='undefined'?pMessage:'Time Measurement';let tmpEndTime=+new Date();let tmpMs=parseInt(pTimeDelta%1000);let tmpSeconds=parseInt(pTimeDelta/1000%60);let tmpMinutes=parseInt(pTimeDelta/(1000*60)%60);let tmpHours=parseInt(pTimeDelta/(1000*60*60));tmpMs=tmpMs<10?"00"+tmpMs:tmpMs<100?"0"+tmpMs:tmpMs;tmpSeconds=tmpSeconds<10?"0"+tmpSeconds:tmpSeconds;tmpMinutes=tmpMinutes<10?"0"+tmpMinutes:tmpMinutes;tmpHours=tmpHours<10?"0"+tmpHours:tmpHours;this.info(`${tmpMessage} logged at (epoch ${+tmpEndTime}) took (${pTimeDelta}ms) or (${tmpHours}:${tmpMinutes}:${tmpSeconds}.${tmpMs})`,pDatum);}logTimeDeltaRelative(pStartTime,pMessage,pDatum){this.logTimeDelta(this.getTimeDelta(pStartTime),pMessage,pDatum);}logTimeDeltaRelativeHuman(pStartTime,pMessage,pDatum){this.logTimeDeltaHuman(this.getTimeDelta(pStartTime),pMessage,pDatum);}}module.exports=FableLog;module.exports.LogProviderBase=require('./Fable-Log-BaseLogger.js');module.exports.LogProviderConsole=require('./Fable-Log-Logger-Console.js');module.exports.LogProviderFlatfile=require('./Fable-Log-Logger-SimpleFlatFile.js');},{"../package.json":51,"./Fable-Log-BaseLogger.js":52,"./Fable-Log-DefaultProviders-Node.js":53,"./Fable-Log-DefaultStreams.json":54,"./Fable-Log-Logger-Console.js":55,"./Fable-Log-Logger-SimpleFlatFile.js":56,"fable-serviceproviderbase":59}],58:[function(require,module,exports){module.exports={"name":"fable-serviceproviderbase","version":"3.0.17","description":"Simple base classes for fable services.","main":"source/Fable-ServiceProviderBase.js","scripts":{"start":"node source/Fable-ServiceProviderBase.js","test":"npx mocha -u tdd -R spec","tests":"npx mocha -u tdd --exit -R spec --grep","coverage":"npx nyc --reporter=lcov --reporter=text-lcov npx mocha -- -u tdd -R spec","build":"npx quack build","types":"tsc -p ./tsconfig.build.json","check":"tsc -p . --noEmit"},"types":"types/source/Fable-ServiceProviderBase.d.ts","mocha":{"diff":true,"extension":["js"],"package":"./package.json","reporter":"spec","slow":"75","timeout":"5000","ui":"tdd","watch-files":["source/**/*.js","test/**/*.js"],"watch-ignore":["lib/vendor"]},"repository":{"type":"git","url":"https://github.com/stevenvelozo/fable-serviceproviderbase.git"},"keywords":["entity","behavior"],"author":"Steven Velozo <steven@velozo.com> (http://velozo.com/)","license":"MIT","bugs":{"url":"https://github.com/stevenvelozo/fable-serviceproviderbase/issues"},"homepage":"https://github.com/stevenvelozo/fable-serviceproviderbase","devDependencies":{"@types/mocha":"^10.0.10","fable":"^3.1.51","quackage":"^1.0.45","typescript":"^5.9.3"}};},{}],59:[function(require,module,exports){/**
|
|
671
671
|
* Fable Service Base
|
|
672
672
|
* @author <steven@velozo.com>
|
|
673
673
|
*/const libPackage=require('../package.json');class FableServiceProviderBase{/**
|
|
@@ -688,7 +688,7 @@ this.serviceType=`Unknown-${this.UUID}`;// The service hash is used to identify
|
|
|
688
688
|
this.Hash=typeof pServiceHash==='string'?pServiceHash:!this.fable&&typeof pOptions==='string'?pOptions:`${this.UUID}`;}/**
|
|
689
689
|
* @param {import('fable')} pFable
|
|
690
690
|
*/connectFable(pFable){if(typeof pFable!=='object'||!pFable.isFable){let tmpErrorMessage=`Fable Service Provider Base: Cannot connect to Fable, invalid Fable object passed in. The pFable parameter was a [${typeof pFable}].}`;console.log(tmpErrorMessage);return new Error(tmpErrorMessage);}if(!this.fable){this.fable=pFable;}if(!this.log){this.log=this.fable.Logging;}if(!this.services){this.services=this.fable.services;}if(!this.servicesMap){this.servicesMap=this.fable.servicesMap;}return true;}}_defineProperty2(FableServiceProviderBase,"isFableService",true);module.exports=FableServiceProviderBase;// This is left here in case we want to go back to having different code/base class for "core" services
|
|
691
|
-
module.exports.CoreServiceProviderBase=FableServiceProviderBase;},{"../package.json":58}],60:[function(require,module,exports){module.exports={"name":"fable-settings","version":"3.0.
|
|
691
|
+
module.exports.CoreServiceProviderBase=FableServiceProviderBase;},{"../package.json":58}],60:[function(require,module,exports){module.exports={"name":"fable-settings","version":"3.0.14","description":"A simple, tolerant configuration chain.","main":"source/Fable-Settings.js","scripts":{"start":"node source/Fable-Settings.js","coverage":"./node_modules/.bin/nyc --reporter=lcov --reporter=text-lcov ./node_modules/mocha/bin/_mocha -- -u tdd -R spec","test":"./node_modules/.bin/mocha -u tdd -R spec","build":"./node_modules/.bin/gulp build","docker-dev-build-image":"docker build ./ -f Dockerfile_LUXURYCode -t retold/fable-settings:local","docker-dev-run":"docker run -it -d --name retold-fable-settings-dev -p 30003:8080 -v \"$PWD/.config:/home/coder/.config\" -v \"$PWD:/home/coder/fable-settings\" -u \"$(id -u):$(id -g)\" -e \"DOCKER_USER=$USER\" retold/fable-settings:local"},"mocha":{"diff":true,"extension":["js"],"package":"./package.json","reporter":"spec","slow":"75","timeout":"5000","ui":"tdd","watch-files":["source/**/*.js","test/**/*.js"],"watch-ignore":["lib/vendor"]},"repository":{"type":"git","url":"https://github.com/stevenvelozo/fable-settings.git"},"keywords":["configuration"],"author":"Steven Velozo <steven@velozo.com> (http://velozo.com/)","license":"MIT","bugs":{"url":"https://github.com/stevenvelozo/fable-settings/issues"},"homepage":"https://github.com/stevenvelozo/fable-settings","devDependencies":{"quackage":"^1.0.48"},"dependencies":{"fable-serviceproviderbase":"^3.0.17","precedent":"^1.0.15"}};},{}],61:[function(require,module,exports){module.exports={"Product":"ApplicationNameHere","ProductVersion":"0.0.0","ConfigFile":false,"LogStreams":[{"level":"trace"}]};},{}],62:[function(require,module,exports){(function(process){(function(){/**
|
|
692
692
|
* Fable Settings Template Processor
|
|
693
693
|
*
|
|
694
694
|
* This class allows environment variables to come in via templated expressions, and defaults to be set.
|
|
@@ -969,7 +969,7 @@ return false;}// Now see if the function has arguments.
|
|
|
969
969
|
let tmpFunctionArguments=_MockFable.DataFormat.stringGetSegments(_MockFable.DataFormat.stringGetEnclosureValueByIndex(tmpSubObjectName.substring(tmpFunctionAddress.length),0),',');if(tmpFunctionArguments.length==0||tmpFunctionArguments[0]==''){// No arguments... just call the function (bound to the scope of the object it is contained withing)
|
|
970
970
|
if(tmpFunctionAddress in pObject){try{return this.checkAddressExists(pObject[tmpFunctionAddress].apply(pObject),tmpNewAddress,tmpRootObject);}catch(pError){// The function call failed, so the address doesn't exist
|
|
971
971
|
libSimpleLog(`Error calling function ${tmpFunctionAddress} (address [${pAddress}]): ${pError.message}`);return false;}}else{// The function doesn't exist, so the address doesn't exist
|
|
972
|
-
libSimpleLog(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[]
|
|
972
|
+
libSimpleLog(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[];// Now get the value for each argument
|
|
973
973
|
for(let i=0;i<tmpFunctionArguments.length;i++){// Resolve the values for each subsequent entry
|
|
974
974
|
// NOTE: This is where the resolves get really tricky. Recursion within recursion. Programming gom jabbar, yo.
|
|
975
975
|
tmpArgumentValues.push(this.getObjectValueClass.getValueAtAddress(tmpRootObject,tmpFunctionArguments[i]));}//return this.checkAddressExists(pObject[tmpFunctionAddress].apply(pObject, tmpArgumentValues), tmpNewAddress, tmpRootObject);
|
|
@@ -1011,10 +1011,10 @@ return this.checkAddressExists(pObject[tmpBoxedPropertyName][tmpBoxedPropertyRef
|
|
|
1011
1011
|
return this.checkAddressExists(pObject[tmpBoxedPropertyName][tmpBoxedPropertyNumber],tmpNewAddress,tmpRootObject);}}// If there is an object property already named for the sub object, but it isn't an object
|
|
1012
1012
|
// then the system can't set the value in there. Error and abort!
|
|
1013
1013
|
if(tmpSubObjectName in pObject&&typeof pObject[tmpSubObjectName]!=='object'){return false;}else if(tmpSubObjectName in pObject){// If there is already a subobject pass that to the recursive thingy
|
|
1014
|
-
return this.checkAddressExists(pObject[tmpSubObjectName],tmpNewAddress,tmpRootObject);}else{//
|
|
1015
|
-
|
|
1014
|
+
return this.checkAddressExists(pObject[tmpSubObjectName],tmpNewAddress,tmpRootObject);}else{// The sub-object doesn't exist, so the address doesn't exist
|
|
1015
|
+
return false;}}}}module.exports=ManyfestObjectAddressResolverCheckAddressExists;},{"./Manyfest-CleanWrapCharacters.js":81,"./Manyfest-LogToConsole.js":83,"./Manyfest-ObjectAddress-GetValue.js":86,"./Manyfest-ObjectAddress-Parser.js":87}],85:[function(require,module,exports){/**
|
|
1016
1016
|
* @author <steven@velozo.com>
|
|
1017
|
-
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');let fCleanWrapCharacters=require('./Manyfest-CleanWrapCharacters.js');let fParseConditionals=require(`../source/Manyfest-ParseConditionals.js`);/**
|
|
1017
|
+
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');let fCleanWrapCharacters=require('./Manyfest-CleanWrapCharacters.js');let fParseConditionals=require(`../source/Manyfest-ParseConditionals.js`);let _MockFable={DataFormat:require('./Manyfest-ObjectAddress-Parser.js')};/**
|
|
1018
1018
|
* Object Address Resolver - DeleteValue
|
|
1019
1019
|
*
|
|
1020
1020
|
* IMPORTANT NOTE: This code is intentionally more verbose than necessary, to
|
|
@@ -1054,9 +1054,9 @@ this.logInfo=typeof pInfoLog=='function'?pInfoLog:libSimpleLog;this.logError=typ
|
|
|
1054
1054
|
*/deleteValueAtAddress(pObject,pAddress,pParentAddress){// Make sure pObject (the object we are meant to be recursing) is an object (which could be an array or object)
|
|
1055
1055
|
if(typeof pObject!='object')return undefined;// Make sure pAddress (the address we are resolving) is a string
|
|
1056
1056
|
if(typeof pAddress!='string')return undefined;// Stash the parent address for later resolution
|
|
1057
|
-
let tmpParentAddress="";if(typeof pParentAddress=='string'){tmpParentAddress=pParentAddress;}//
|
|
1058
|
-
let
|
|
1059
|
-
if(
|
|
1057
|
+
let tmpParentAddress="";if(typeof pParentAddress=='string'){tmpParentAddress=pParentAddress;}// Use enclosure-aware parser to find the first segment separator
|
|
1058
|
+
let tmpAddressPartBeginning=_MockFable.DataFormat.stringGetFirstSegment(pAddress);// This is the terminal address string (no more dots so the RECUSION ENDS IN HERE somehow)
|
|
1059
|
+
if(tmpAddressPartBeginning.length==pAddress.length){// Check if the address refers to a boxed property
|
|
1060
1060
|
let tmpBracketStartIndex=pAddress.indexOf('[');let tmpBracketStopIndex=pAddress.indexOf(']');// Check for the Object Set Type marker.
|
|
1061
1061
|
// Note this will not work with a bracket in the same address box set
|
|
1062
1062
|
let tmpObjectTypeMarkerIndex=pAddress.indexOf('{}');// Boxed elements look like this:
|
|
@@ -1096,7 +1096,7 @@ let tmpKeepRecord=this.checkRecordFilters(pAddress,tmpInputArray[i]);if(tmpKeepR
|
|
|
1096
1096
|
tmpInputArray.splice(i,1);}}return true;}// The object has been flagged as an object set, so treat it as such
|
|
1097
1097
|
else if(tmpObjectTypeMarkerIndex>0){let tmpObjectPropertyName=pAddress.substring(0,tmpObjectTypeMarkerIndex).trim();if(typeof pObject[tmpObjectPropertyName]!='object'){// We asked for a set from an array but it isnt' an array.
|
|
1098
1098
|
return false;}delete pObject[tmpObjectPropertyName];return true;}else{// Now is the point in recursion to return the value in the address
|
|
1099
|
-
delete pObject[pAddress];return true;}}else{let tmpSubObjectName=
|
|
1099
|
+
delete pObject[pAddress];return true;}}else{let tmpSubObjectName=tmpAddressPartBeginning;let tmpNewAddress=pAddress.substring(tmpAddressPartBeginning.length+1);// BOXED ELEMENTS
|
|
1100
1100
|
// Test if the tmpNewAddress is an array or object
|
|
1101
1101
|
// Check if it's a boxed property
|
|
1102
1102
|
let tmpBracketStartIndex=tmpSubObjectName.indexOf('[');let tmpBracketStopIndex=tmpSubObjectName.indexOf(']');// Boxed elements look like this:
|
|
@@ -1154,7 +1154,7 @@ if(tmpSubObjectName in pObject&&typeof pObject[tmpSubObjectName]!=='object'){ret
|
|
|
1154
1154
|
// Continue to manage the parent address for recursion
|
|
1155
1155
|
tmpParentAddress=`${tmpParentAddress}${tmpParentAddress.length>0?'.':''}${tmpSubObjectName}`;return this.deleteValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,tmpParentAddress);}else{// Create a subobject and then pass that
|
|
1156
1156
|
// Continue to manage the parent address for recursion
|
|
1157
|
-
tmpParentAddress=`${tmpParentAddress}${tmpParentAddress.length>0?'.':''}${tmpSubObjectName}`;pObject[tmpSubObjectName]={};return this.deleteValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,tmpParentAddress);}}}};module.exports=ManyfestObjectAddressResolverDeleteValue;},{"../source/Manyfest-ParseConditionals.js":90,"./Manyfest-CleanWrapCharacters.js":81,"./Manyfest-LogToConsole.js":83}],86:[function(require,module,exports){/**
|
|
1157
|
+
tmpParentAddress=`${tmpParentAddress}${tmpParentAddress.length>0?'.':''}${tmpSubObjectName}`;pObject[tmpSubObjectName]={};return this.deleteValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,tmpParentAddress);}}}};module.exports=ManyfestObjectAddressResolverDeleteValue;},{"../source/Manyfest-ParseConditionals.js":90,"./Manyfest-CleanWrapCharacters.js":81,"./Manyfest-LogToConsole.js":83,"./Manyfest-ObjectAddress-Parser.js":87}],86:[function(require,module,exports){/**
|
|
1158
1158
|
* @author <steven@velozo.com>
|
|
1159
1159
|
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');let fCleanWrapCharacters=require('./Manyfest-CleanWrapCharacters.js');let fParseConditionals=require(`../source/Manyfest-ParseConditionals.js`);let _MockFable={DataFormat:require('./Manyfest-ObjectAddress-Parser.js')};/**
|
|
1160
1160
|
* Object Address Resolver - GetValue
|
|
@@ -1233,7 +1233,7 @@ return false;}// Now see if the function has arguments.
|
|
|
1233
1233
|
let tmpFunctionArguments=_MockFable.DataFormat.stringGetSegments(_MockFable.DataFormat.stringGetEnclosureValueByIndex(pAddress.substring(tmpFunctionAddress.length),0),',');if(tmpFunctionArguments.length==0||tmpFunctionArguments[0]==''){// No arguments... just call the function (bound to the scope of the object it is contained withing)
|
|
1234
1234
|
if(tmpFunctionAddress in pObject){try{return pObject[tmpFunctionAddress].apply(pObject);}catch(pError){// The function call failed, so the address doesn't exist
|
|
1235
1235
|
console.log(`Error in getValueAtAddress calling function ${tmpFunctionAddress} (address [${pAddress}]): ${pError.message}`);return false;}}else{// The function doesn't exist, so the address doesn't exist
|
|
1236
|
-
console.log(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[]
|
|
1236
|
+
console.log(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[];// Now get the value for each argument
|
|
1237
1237
|
for(let i=0;i<tmpFunctionArguments.length;i++){// Resolve the values for each subsequent entry
|
|
1238
1238
|
// Check if the argument value is a string literal or a reference to an address
|
|
1239
1239
|
if(tmpFunctionArguments[i].length>=2&&(tmpFunctionArguments[i].charAt(0)=='"'||tmpFunctionArguments[i].charAt(0)=="'"||tmpFunctionArguments[i].charAt(0)=="`")&&(tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=='"'||tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=="'"||tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=="`")){// This is a string literal
|
|
@@ -1275,7 +1275,7 @@ return false;}let tmpInputArray=pObject[tmpBoxedPropertyName];let tmpOutputArray
|
|
|
1275
1275
|
let tmpKeepRecord=this.checkRecordFilters(pAddress,tmpInputArray[i]);if(tmpKeepRecord){tmpOutputArray.push(tmpInputArray[i]);}}return tmpOutputArray;}// The object has been flagged as an object set, so treat it as such
|
|
1276
1276
|
else if(tmpObjectTypeMarkerIndex>0){let tmpObjectPropertyName=pAddress.substring(0,tmpObjectTypeMarkerIndex).trim();if(typeof pObject[tmpObjectPropertyName]!='object'){// We asked for a set from an array but it isnt' an array.
|
|
1277
1277
|
return false;}return pObject[tmpObjectPropertyName];}else{// Now is the point in recursion to return the value in the address
|
|
1278
|
-
if(typeof pObject[pAddress]!=
|
|
1278
|
+
if(typeof pObject[pAddress]!='undefined'){return pObject[pAddress];}else{return undefined;}}}else{//let tmpSubObjectName = pAddress.substring(0, tmpSeparatorIndex);
|
|
1279
1279
|
//let tmpNewAddress = pAddress.substring(tmpSeparatorIndex+1);
|
|
1280
1280
|
let tmpSubObjectName=tmpAddressPartBeginning;let tmpNewAddress=pAddress.substring(tmpAddressPartBeginning.length+1);// BOXED ELEMENTS
|
|
1281
1281
|
// Test if the tmpNewAddress is an array or object
|
|
@@ -1300,7 +1300,7 @@ return false;}// Now see if the function has arguments.
|
|
|
1300
1300
|
let tmpFunctionArguments=_MockFable.DataFormat.stringGetSegments(_MockFable.DataFormat.stringGetEnclosureValueByIndex(tmpSubObjectName.substring(tmpFunctionAddress.length),0),',');if(tmpFunctionArguments.length==0||tmpFunctionArguments[0]==''){// No arguments... just call the function (bound to the scope of the object it is contained withing)
|
|
1301
1301
|
if(tmpFunctionAddress in pObject){try{return this.getValueAtAddress(pObject[tmpFunctionAddress].apply(pObject),tmpNewAddress,tmpParentAddress,tmpRootObject);}catch(pError){// The function call failed, so the address doesn't exist
|
|
1302
1302
|
console.log(`Error in getValueAtAddress calling function ${tmpFunctionAddress} (address [${pAddress}]): ${pError.message}`);return false;}}else{// The function doesn't exist, so the address doesn't exist
|
|
1303
|
-
console.log(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[]
|
|
1303
|
+
console.log(`Function ${tmpFunctionAddress} does not exist (address [${pAddress}])`);return false;}}else{let tmpArgumentValues=[];// Now get the value for each argument
|
|
1304
1304
|
for(let i=0;i<tmpFunctionArguments.length;i++){// Resolve the values for each subsequent entry
|
|
1305
1305
|
// Check if the argument value is a string literal or a reference to an address
|
|
1306
1306
|
if(tmpFunctionArguments[i].length>=2&&(tmpFunctionArguments[i].charAt(0)=='"'||tmpFunctionArguments[i].charAt(0)=="'"||tmpFunctionArguments[i].charAt(0)=="`")&&(tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=='"'||tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=="'"||tmpFunctionArguments[i].charAt(tmpFunctionArguments[i].length-1)=="`")){// This is a string literal
|
|
@@ -1377,7 +1377,7 @@ const DEFAULT_START_SYMBOL_MAP={'{':0,'[':1,'(':2};const DEFAULT_END_SYMBOL_MAP=
|
|
|
1377
1377
|
* @param {Record<string, number>} [pEnclosureEndSymbolMap]
|
|
1378
1378
|
*
|
|
1379
1379
|
* @return {number} - The number of segments in the string
|
|
1380
|
-
*/stringCountSegments:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;if(
|
|
1380
|
+
*/stringCountSegments:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;if(tmpString.length<1){return 0;}let tmpSegmentCount=1;let tmpEnclosureStack=[];for(let i=0;i<tmpString.length;i++){// IF This is the start of a segment
|
|
1381
1381
|
if(tmpString[i]==tmpSeparator// AND we are not in a nested portion of the string
|
|
1382
1382
|
&&tmpEnclosureStack.length==0){// Increment the segment count
|
|
1383
1383
|
tmpSegmentCount++;}// IF This is the start of an enclosure
|
|
@@ -1394,7 +1394,7 @@ tmpEnclosureStack.pop();}}return tmpSegmentCount;},/**
|
|
|
1394
1394
|
* @param {Record<string, number>} [pEnclosureEndSymbolMap]
|
|
1395
1395
|
*
|
|
1396
1396
|
* @return {string} - the first segment in the string as a string
|
|
1397
|
-
*/stringGetFirstSegment:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;if(
|
|
1397
|
+
*/stringGetFirstSegment:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;if(tmpString.length<1){return'';}let tmpEnclosureStack=[];for(let i=0;i<tmpString.length;i++){// IF This is the start of a segment
|
|
1398
1398
|
if(tmpString[i]==tmpSeparator// AND we are not in a nested portion of the string
|
|
1399
1399
|
&&tmpEnclosureStack.length==0){// Return the segment
|
|
1400
1400
|
return tmpString.substring(0,i);}// IF This is the start of an enclosure
|
|
@@ -1411,7 +1411,7 @@ tmpEnclosureStack.pop();}}return tmpString;},/**
|
|
|
1411
1411
|
* @param {Record<string, number>} [pEnclosureEndSymbolMap]
|
|
1412
1412
|
*
|
|
1413
1413
|
* @return {Array<string>} - the segments in the string as an array of strings
|
|
1414
|
-
*/stringGetSegments:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;let tmpCurrentSegmentStart=0;let tmpSegmentList=[];if(
|
|
1414
|
+
*/stringGetSegments:(pString,pSeparator,pEnclosureStartSymbolMap,pEnclosureEndSymbolMap)=>{let tmpString=typeof pString=='string'?pString:'';let tmpSeparator=typeof pSeparator=='string'?pSeparator:'.';let tmpEnclosureStartSymbolMap=typeof pEnclosureStartSymbolMap=='object'?pEnclosureStartSymbolMap:DEFAULT_START_SYMBOL_MAP;let tmpEnclosureEndSymbolMap=typeof pEnclosureEndSymbolMap=='object'?pEnclosureEndSymbolMap:DEFAULT_END_SYMBOL_MAP;let tmpCurrentSegmentStart=0;let tmpSegmentList=[];if(tmpString.length<1){return tmpSegmentList;}let tmpEnclosureStack=[];for(let i=0;i<tmpString.length;i++){// IF This is the start of a segment
|
|
1415
1415
|
if(tmpString[i]==tmpSeparator// AND we are not in a nested portion of the string
|
|
1416
1416
|
&&tmpEnclosureStack.length==0){// Return the segment
|
|
1417
1417
|
tmpSegmentList.push(tmpString.substring(tmpCurrentSegmentStart,i));tmpCurrentSegmentStart=i+1;}// IF This is the start of an enclosure
|
|
@@ -1448,7 +1448,7 @@ else if(tmpString[i]==tmpEnclosureEnd){tmpEnclosureDepth--;// Again, only count
|
|
|
1448
1448
|
if(tmpEnclosureDepth==0&&tmpMatchedEnclosureIndex&&tmpEnclosedValueEndIndex<=tmpEnclosedValueStartIndex){tmpEnclosedValueEndIndex=i;tmpMatchedEnclosureIndex=false;}}}if(tmpEnclosureCount<=tmpEnclosureIndexToGet){// Return an empty string if the enclosure is not found
|
|
1449
1449
|
return'';}if(tmpEnclosedValueEndIndex>0&&tmpEnclosedValueEndIndex>tmpEnclosedValueStartIndex){return tmpString.substring(tmpEnclosedValueStartIndex+1,tmpEnclosedValueEndIndex);}else{return tmpString.substring(tmpEnclosedValueStartIndex+1);}}};},{}],88:[function(require,module,exports){/**
|
|
1450
1450
|
* @author <steven@velozo.com>
|
|
1451
|
-
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');let fCleanWrapCharacters=require('./Manyfest-CleanWrapCharacters.js');/**
|
|
1451
|
+
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');let fCleanWrapCharacters=require('./Manyfest-CleanWrapCharacters.js');let _MockFable={DataFormat:require('./Manyfest-ObjectAddress-Parser.js')};/**
|
|
1452
1452
|
* Object Address Resolver - SetValue
|
|
1453
1453
|
*
|
|
1454
1454
|
* IMPORTANT NOTE: This code is intentionally more verbose than necessary, to
|
|
@@ -1479,7 +1479,8 @@ this.logInfo=typeof pInfoLog=='function'?pInfoLog:libSimpleLog;this.logError=typ
|
|
|
1479
1479
|
* @return {boolean} True if the value was set, false otherwise
|
|
1480
1480
|
*/setValueAtAddress(pObject,pAddress,pValue){// Make sure pObject is an object
|
|
1481
1481
|
if(typeof pObject!='object')return false;// Make sure pAddress is a string
|
|
1482
|
-
if(typeof pAddress!='string')return false
|
|
1482
|
+
if(typeof pAddress!='string')return false;// Use enclosure-aware parser to find the first segment separator
|
|
1483
|
+
let tmpAddressPartBeginning=_MockFable.DataFormat.stringGetFirstSegment(pAddress);if(tmpAddressPartBeginning.length==pAddress.length){// Check if it's a boxed property
|
|
1483
1484
|
let tmpBracketStartIndex=pAddress.indexOf('[');let tmpBracketStopIndex=pAddress.indexOf(']');// Boxed elements look like this:
|
|
1484
1485
|
// MyValues[10]
|
|
1485
1486
|
// MyValues['Name']
|
|
@@ -1510,7 +1511,7 @@ pObject[tmpBoxedPropertyName][tmpBoxedPropertyReference]={};}// Return the value
|
|
|
1510
1511
|
//TODO: For cases where we have chained [][] properties, this needs to recurse somehow
|
|
1511
1512
|
pObject[tmpBoxedPropertyName][tmpBoxedPropertyReference]=pValue;return true;}else{while(pObject[tmpBoxedPropertyName].length<tmpBoxedPropertyNumber+1){// If the subobject doesn't exist, create it
|
|
1512
1513
|
pObject[tmpBoxedPropertyName].push({});}pObject[tmpBoxedPropertyName][tmpBoxedPropertyNumber]=pValue;return true;}}else{// Now is the time in recursion to set the value in the object
|
|
1513
|
-
pObject[pAddress]=pValue;return true;}}else{let tmpSubObjectName=
|
|
1514
|
+
pObject[pAddress]=pValue;return true;}}else{let tmpSubObjectName=tmpAddressPartBeginning;let tmpNewAddress=pAddress.substring(tmpAddressPartBeginning.length+1);// Test if the tmpNewAddress is an array or object
|
|
1514
1515
|
// Check if it's a boxed property
|
|
1515
1516
|
let tmpBracketStartIndex=tmpSubObjectName.indexOf('[');let tmpBracketStopIndex=tmpSubObjectName.indexOf(']');// Boxed elements look like this:
|
|
1516
1517
|
// MyValues[42]
|
|
@@ -1551,7 +1552,7 @@ return this.setValueAtAddress(pObject[tmpBoxedPropertyName][tmpBoxedPropertyNumb
|
|
|
1551
1552
|
if(tmpSubObjectName in pObject&&typeof pObject[tmpSubObjectName]!=='object'){if(!('__ERROR'in pObject))pObject['__ERROR']={};// Put it in an error object so data isn't lost
|
|
1552
1553
|
pObject['__ERROR'][pAddress]=pValue;return false;}else if(tmpSubObjectName in pObject){// If there is already a subobject pass that to the recursive thingy
|
|
1553
1554
|
return this.setValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,pValue);}else{// Create a subobject and then pass that
|
|
1554
|
-
pObject[tmpSubObjectName]={};return this.setValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,pValue);}}}};module.exports=ManyfestObjectAddressSetValue;},{"./Manyfest-CleanWrapCharacters.js":81,"./Manyfest-LogToConsole.js":83}],89:[function(require,module,exports){/**
|
|
1555
|
+
pObject[tmpSubObjectName]={};return this.setValueAtAddress(pObject[tmpSubObjectName],tmpNewAddress,pValue);}}}};module.exports=ManyfestObjectAddressSetValue;},{"./Manyfest-CleanWrapCharacters.js":81,"./Manyfest-LogToConsole.js":83,"./Manyfest-ObjectAddress-Parser.js":87}],89:[function(require,module,exports){/**
|
|
1555
1556
|
* @author <steven@velozo.com>
|
|
1556
1557
|
*/let libSimpleLog=require('./Manyfest-LogToConsole.js');/**
|
|
1557
1558
|
* Object Address Generation
|
|
@@ -1611,7 +1612,7 @@ break;}return tmpSchema;}};module.exports=ManyfestObjectAddressGeneration;},{"./
|
|
|
1611
1612
|
const _ConditionalStanzaStart='<<~?';const _ConditionalStanzaStartLength=_ConditionalStanzaStart.length;const _ConditionalStanzaEnd='?~>>';const _ConditionalStanzaEndLength=_ConditionalStanzaEnd.length;// Ugh dependency injection. Can't wait to make these all fable services.
|
|
1612
1613
|
//let libObjectAddressCheckAddressExists = new (require('./Manyfest-ObjectAddress-CheckAddressExists.js'))();
|
|
1613
1614
|
// Test the condition of a value in a record
|
|
1614
|
-
const testCondition=(pManyfest,pRecord,pSearchAddress,pSearchComparator,pValue)=>{switch(pSearchComparator){case'TRUE':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)===true;
|
|
1615
|
+
const testCondition=(pManyfest,pRecord,pSearchAddress,pSearchComparator,pValue)=>{switch(pSearchComparator){case'TRUE':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)===true;case'FALSE':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)===false;case'LNGT':case'LENGTH_GREATER_THAN':switch(typeof pManyfest.getValueAtAddress(pRecord,pSearchAddress)){case'string':return pManyfest.getValueAtAddress(pRecord,pSearchAddress).length>pValue;case'object':return pManyfest.getValueAtAddress(pRecord,pSearchAddress).length>pValue;default:return false;break;}break;case'LNLT':case'LENGTH_LESS_THAN':switch(typeof pManyfest.getValueAtAddress(pRecord,pSearchAddress)){case'string':return pManyfest.getValueAtAddress(pRecord,pSearchAddress).length<pValue;case'object':return pManyfest.getValueAtAddress(pRecord,pSearchAddress).length<pValue;default:return false;break;}break;// TODO: Welcome to dependency hell. This fixes itself when we move to fable services.
|
|
1615
1616
|
// case 'EX':
|
|
1616
1617
|
// case 'EXISTS':
|
|
1617
1618
|
// return libObjectAddressCheckAddressExists.checkAddressExists(pRecord, pSearchAddress);
|
|
@@ -1620,7 +1621,7 @@ const testCondition=(pManyfest,pRecord,pSearchAddress,pSearchComparator,pValue)=
|
|
|
1620
1621
|
// case 'DOES_NOT_EXIST':
|
|
1621
1622
|
// return !libObjectAddressCheckAddressExists.checkAddressExists(pRecord, pSearchAddress);
|
|
1622
1623
|
// break;
|
|
1623
|
-
case'!=':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)!=pValue;
|
|
1624
|
+
case'!=':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)!=pValue;case'<':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)<pValue;case'>':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)>pValue;case'<=':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)<=pValue;case'>=':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)>=pValue;case'===':return pManyfest.getValueAtAddress(pRecord,pSearchAddress)===pValue;case'==':default:return pManyfest.getValueAtAddress(pRecord,pSearchAddress)==pValue;}};const parseConditionals=(pManyfest,pAddress,pRecord)=>{let tmpKeepRecord=true;/*
|
|
1624
1625
|
Algorithm is simple:
|
|
1625
1626
|
|
|
1626
1627
|
1. Enuerate start points
|
|
@@ -1714,9 +1715,8 @@ tmpNewManyfest.hashTranslations.addTranslation(this.hashTranslations.translation
|
|
|
1714
1715
|
* @return {Manyfest} The deserialized manifest
|
|
1715
1716
|
*/deserialize(pManifestString){// TODO: Add guards for bad manifest string
|
|
1716
1717
|
this.loadManifest(JSON.parse(pManifestString));return this;}// Load a manifest from an object
|
|
1717
|
-
loadManifest(pManifest){if(typeof pManifest!=='object'){this.logError(`(${this.scope}) Error loading manifest; expecting an object but parameter was type ${typeof pManifest}.`);}let tmpManifest=typeof pManifest=='object'?pManifest:{};let tmpDescriptorKeys=Object.keys(_DefaultConfiguration);for(let i=0;i<tmpDescriptorKeys.length;i++){if(!(tmpDescriptorKeys[i]in tmpManifest)){tmpManifest[tmpDescriptorKeys[i]]=JSON.parse(JSON.stringify(_DefaultConfiguration[tmpDescriptorKeys[i]]));}}if('Scope'in tmpManifest){if(typeof tmpManifest.Scope==='string'){this.scope=tmpManifest.Scope;}else{this.logError(`(${this.scope}) Error loading scope from manifest; expecting a string but property was type ${typeof tmpManifest.Scope}.`,tmpManifest);}}else{this.logError(`(${this.scope}) Error loading scope from manifest object. Property "Scope" does not exist in the root of the object.`,tmpManifest);}if('Descriptors'in tmpManifest){if(typeof tmpManifest.Descriptors==='object'){let tmpDescriptionAddresses=Object.keys(tmpManifest.Descriptors);for(let i=0;i<tmpDescriptionAddresses.length;i++){this.addDescriptor(tmpDescriptionAddresses[i],tmpManifest.Descriptors[tmpDescriptionAddresses[i]]);}}else{this.logError(`(${this.scope}) Error loading description object from manifest object. Expecting an object in 'Manifest.Descriptors' but the property was type ${typeof tmpManifest.Descriptors}.`,tmpManifest);}}else{this.logError(`(${this.scope}) Error loading object description from manifest object. Property "Descriptors" does not exist in the root of the Manifest object.`,tmpManifest);}if('HashTranslations'in tmpManifest){if(typeof tmpManifest.HashTranslations==='object'){
|
|
1718
|
-
|
|
1719
|
-
}}}}/**
|
|
1718
|
+
loadManifest(pManifest){if(typeof pManifest!=='object'){this.logError(`(${this.scope}) Error loading manifest; expecting an object but parameter was type ${typeof pManifest}.`);}let tmpManifest=typeof pManifest=='object'?pManifest:{};let tmpDescriptorKeys=Object.keys(_DefaultConfiguration);for(let i=0;i<tmpDescriptorKeys.length;i++){if(!(tmpDescriptorKeys[i]in tmpManifest)){tmpManifest[tmpDescriptorKeys[i]]=JSON.parse(JSON.stringify(_DefaultConfiguration[tmpDescriptorKeys[i]]));}}if('Scope'in tmpManifest){if(typeof tmpManifest.Scope==='string'){this.scope=tmpManifest.Scope;}else{this.logError(`(${this.scope}) Error loading scope from manifest; expecting a string but property was type ${typeof tmpManifest.Scope}.`,tmpManifest);}}else{this.logError(`(${this.scope}) Error loading scope from manifest object. Property "Scope" does not exist in the root of the object.`,tmpManifest);}if('Descriptors'in tmpManifest){if(typeof tmpManifest.Descriptors==='object'){let tmpDescriptionAddresses=Object.keys(tmpManifest.Descriptors);for(let i=0;i<tmpDescriptionAddresses.length;i++){this.addDescriptor(tmpDescriptionAddresses[i],tmpManifest.Descriptors[tmpDescriptionAddresses[i]]);}}else{this.logError(`(${this.scope}) Error loading description object from manifest object. Expecting an object in 'Manifest.Descriptors' but the property was type ${typeof tmpManifest.Descriptors}.`,tmpManifest);}}else{this.logError(`(${this.scope}) Error loading object description from manifest object. Property "Descriptors" does not exist in the root of the Manifest object.`,tmpManifest);}if('HashTranslations'in tmpManifest){if(typeof tmpManifest.HashTranslations==='object'){// HashTranslations is serialized as a plain object of source:target pairs
|
|
1719
|
+
this.hashTranslations.addTranslation(tmpManifest.HashTranslations);}}}/**
|
|
1720
1720
|
* Serialize the Manifest to a string
|
|
1721
1721
|
*
|
|
1722
1722
|
* @return {string} - The serialized manifest
|
|
@@ -1755,20 +1755,22 @@ else if(tmpInTranslationTable){tmpAddress=this.hashTranslations.translate(pHash)
|
|
|
1755
1755
|
// TODO: Discuss this ... it is magic but controversial
|
|
1756
1756
|
else{tmpAddress=pHash;}return tmpAddress;}// Get the value of an element by its hash
|
|
1757
1757
|
getValueByHash(pObject,pHash){let tmpValue=this.getValueAtAddress(pObject,this.resolveHashAddress(pHash));if(typeof tmpValue=='undefined'){// Try to get a default if it exists
|
|
1758
|
-
tmpValue=this.getDefaultValue(this.getDescriptorByHash(pHash));}return tmpValue;}lintAddress(pAddress){
|
|
1759
|
-
if(
|
|
1758
|
+
tmpValue=this.getDefaultValue(this.getDescriptorByHash(pHash));}return tmpValue;}lintAddress(pAddress){// Guard against non-string input
|
|
1759
|
+
if(typeof pAddress!='string'){return'';}let tmpLintedAddress=pAddress.trim();// Check for a single trailing . (but not a ..) at the end of the address and remove it.
|
|
1760
|
+
// We must not strip '..' because that is back-navigation syntax.
|
|
1761
|
+
if(tmpLintedAddress.endsWith('.')&&!tmpLintedAddress.endsWith('..')){tmpLintedAddress=tmpLintedAddress.slice(0,-1);}return tmpLintedAddress;}// Get the value of an element at an address
|
|
1760
1762
|
getValueAtAddress(pObject,pAddress){let tmpLintedAddress=this.lintAddress(pAddress);if(tmpLintedAddress==''){this.logError(`(${this.scope}) Error getting value at address; address is an empty string.`,pObject);return undefined;}let tmpValue=this.objectAddressGetValue.getValueAtAddress(pObject,tmpLintedAddress);if(typeof tmpValue=='undefined'){// Try to get a default if it exists
|
|
1761
1763
|
tmpValue=this.getDefaultValue(this.getDescriptor(tmpLintedAddress));}return tmpValue;}// Set the value of an element by its hash
|
|
1762
1764
|
setValueByHash(pObject,pHash,pValue){return this.setValueAtAddress(pObject,this.resolveHashAddress(pHash),pValue);}// Set the value of an element at an address
|
|
1763
1765
|
setValueAtAddress(pObject,pAddress,pValue){let tmpLintedAddress=this.lintAddress(pAddress);return this.objectAddressSetValue.setValueAtAddress(pObject,tmpLintedAddress,pValue);}// Delete the value of an element by its hash
|
|
1764
|
-
deleteValueByHash(pObject,pHash
|
|
1765
|
-
deleteValueAtAddress(pObject,pAddress
|
|
1766
|
+
deleteValueByHash(pObject,pHash){return this.deleteValueAtAddress(pObject,this.resolveHashAddress(pHash));}// Delete the value of an element at an address
|
|
1767
|
+
deleteValueAtAddress(pObject,pAddress){let tmpLintedAddress=this.lintAddress(pAddress);return this.objectAddressDeleteValue.deleteValueAtAddress(pObject,tmpLintedAddress);}// Validate the consistency of an object against the schema
|
|
1766
1768
|
validate(pObject){let tmpValidationData={Error:null,Errors:[],MissingElements:[]};if(typeof pObject!=='object'){tmpValidationData.Error=true;tmpValidationData.Errors.push(`Expected passed in object to be type object but was passed in ${typeof pObject}`);}let addValidationError=(pAddress,pErrorMessage)=>{tmpValidationData.Error=true;tmpValidationData.Errors.push(`Element at address "${pAddress}" ${pErrorMessage}.`);};// Now enumerate through the values and check for anomalies based on the schema
|
|
1767
1769
|
for(let i=0;i<this.elementAddresses.length;i++){let tmpDescriptor=this.getDescriptor(this.elementAddresses[i]);let tmpValueExists=this.checkAddressExists(pObject,tmpDescriptor.Address);let tmpValue=this.getValueAtAddress(pObject,tmpDescriptor.Address);if(typeof tmpValue=='undefined'||!tmpValueExists){// This will technically mean that `Object.Some.Value = undefined` will end up showing as "missing"
|
|
1768
1770
|
// TODO: Do we want to do a different message based on if the property exists but is undefined?
|
|
1769
1771
|
tmpValidationData.MissingElements.push(tmpDescriptor.Address);if(tmpDescriptor.Required||this.options.strict){addValidationError(tmpDescriptor.Address,'is flagged REQUIRED but is not set in the object');}}// Now see if there is a data type specified for this element
|
|
1770
1772
|
if(tmpDescriptor.DataType){let tmpElementType=typeof tmpValue;switch(tmpDescriptor.DataType.toString().trim().toLowerCase()){case'string':if(tmpElementType!='string'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}break;case"precisenumber":if(tmpElementType!='string'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}else if(!this.numberRegex.test(tmpValue)){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is not a valid number`);}break;case'number':if(tmpElementType!='number'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}break;case'integer':if(tmpElementType!='number'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}else{let tmpValueString=tmpValue.toString();if(tmpValueString.indexOf('.')>-1){// TODO: Is this an error?
|
|
1771
|
-
addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but has a decimal point in the number.`);}}break;case'float':if(tmpElementType!='number'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}break;case'datetime':let tmpValueDate=new Date(tmpValue);if(tmpValueDate.toString()=='Invalid Date'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is not parsable as a Date by Javascript`);}default:// Check if this is a string, in the default case
|
|
1773
|
+
addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but has a decimal point in the number.`);}}break;case'float':if(tmpElementType!='number'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}break;case'boolean':if(tmpElementType!='boolean'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is of the type ${tmpElementType}`);}break;case'datetime':let tmpValueDate=new Date(tmpValue);if(tmpValueDate.toString()=='Invalid Date'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} but is not parsable as a Date by Javascript`);}break;default:// Check if this is a string, in the default case
|
|
1772
1774
|
// Note this is only when a DataType is specified and it is an unrecognized data type.
|
|
1773
1775
|
if(tmpElementType!='string'){addValidationError(tmpDescriptor.Address,`has a DataType ${tmpDescriptor.DataType} (which auto-converted to String because it was unrecognized) but is of the type ${tmpElementType}`);}break;}}}return tmpValidationData;}/**
|
|
1774
1776
|
* Returns a default value, or, the default value for the data type (which is overridable with configuration)
|
|
@@ -1776,7 +1778,8 @@ if(tmpElementType!='string'){addValidationError(tmpDescriptor.Address,`has a Dat
|
|
|
1776
1778
|
* @param {ManifestDescriptor} pDescriptor - The descriptor definition.
|
|
1777
1779
|
*/getDefaultValue(pDescriptor){if(typeof pDescriptor!='object'){return undefined;}if('Default'in pDescriptor){return pDescriptor.Default;}else{// Default to a null if it doesn't have a type specified.
|
|
1778
1780
|
// This will ensure a placeholder is created but isn't misinterpreted.
|
|
1779
|
-
let tmpDataType='DataType'in pDescriptor?pDescriptor.DataType:'String';if(tmpDataType in this.options.defaultValues){
|
|
1781
|
+
let tmpDataType='DataType'in pDescriptor?pDescriptor.DataType:'String';if(tmpDataType in this.options.defaultValues){let tmpDefaultValue=this.options.defaultValues[tmpDataType];// Return a copy of mutable defaults (Array and Object) to prevent shared state
|
|
1782
|
+
if(typeof tmpDefaultValue=='object'&&tmpDefaultValue!==null){return JSON.parse(JSON.stringify(tmpDefaultValue));}return tmpDefaultValue;}else{// give up and return null
|
|
1780
1783
|
return null;}}}// Enumerate through the schema and populate default values if they don't exist.
|
|
1781
1784
|
populateDefaults(pObject,pOverwriteProperties){return this.populateObject(pObject,pOverwriteProperties,// This just sets up a simple filter to see if there is a default set.
|
|
1782
1785
|
pDescriptor=>{return'Default'in pDescriptor;});}// Forcefully populate all values even if they don't have defaults.
|
|
@@ -3188,7 +3191,7 @@ try{if(!global.localStorage)return false;}catch(_){return false;}var val=global.
|
|
|
3188
3191
|
// presumably different callback function.
|
|
3189
3192
|
// This makes sure that own properties are retained, so that
|
|
3190
3193
|
// decorations and such are not lost along the way.
|
|
3191
|
-
module.exports=wrappy;function wrappy(fn,cb){if(fn&&cb)return wrappy(fn)(cb);if(typeof fn!=='function')throw new TypeError('need wrapper function');Object.keys(fn).forEach(function(k){wrapper[k]=fn[k];});return wrapper;function wrapper(){var args=new Array(arguments.length);for(var i=0;i<args.length;i++){args[i]=arguments[i];}var ret=fn.apply(this,args);var cb=args[args.length-1];if(typeof ret==='function'&&ret!==cb){Object.keys(cb).forEach(function(k){ret[k]=cb[k];});}return ret;}}},{}],148:[function(require,module,exports){module.exports=extend;var hasOwnProperty=Object.prototype.hasOwnProperty;function extend(){var target={};for(var i=0;i<arguments.length;i++){var source=arguments[i];for(var key in source){if(hasOwnProperty.call(source,key)){target[key]=source[key];}}}return target;}},{}],149:[function(require,module,exports){module.exports={"name":"fable","version":"3.1.
|
|
3194
|
+
module.exports=wrappy;function wrappy(fn,cb){if(fn&&cb)return wrappy(fn)(cb);if(typeof fn!=='function')throw new TypeError('need wrapper function');Object.keys(fn).forEach(function(k){wrapper[k]=fn[k];});return wrapper;function wrapper(){var args=new Array(arguments.length);for(var i=0;i<args.length;i++){args[i]=arguments[i];}var ret=fn.apply(this,args);var cb=args[args.length-1];if(typeof ret==='function'&&ret!==cb){Object.keys(cb).forEach(function(k){ret[k]=cb[k];});}return ret;}}},{}],148:[function(require,module,exports){module.exports=extend;var hasOwnProperty=Object.prototype.hasOwnProperty;function extend(){var target={};for(var i=0;i<arguments.length;i++){var source=arguments[i];for(var key in source){if(hasOwnProperty.call(source,key)){target[key]=source[key];}}}return target;}},{}],149:[function(require,module,exports){module.exports={"name":"fable","version":"3.1.55","description":"A service dependency injection, configuration and logging library.","main":"source/Fable.js","scripts":{"start":"node source/Fable.js","coverage":"./node_modules/.bin/nyc --reporter=lcov --reporter=text-lcov ./node_modules/mocha/bin/_mocha -- -u tdd -R spec","test":"./node_modules/.bin/mocha -u tdd -R spec","build":"npx quack build","docker-dev-build":"docker build ./ -f Dockerfile_LUXURYCode -t fable-image:local","docker-dev-run":"docker run -it -d --name fable-dev -p 30001:8080 -p 38086:8086 -v \"$PWD/.config:/home/coder/.config\" -v \"$PWD:/home/coder/fable\" -u \"$(id -u):$(id -g)\" -e \"DOCKER_USER=$USER\" fable-image:local","docker-dev-shell":"docker exec -it fable-dev /bin/bash","tests":"./node_modules/mocha/bin/_mocha -u tdd --exit -R spec --grep"},"mocha":{"diff":true,"extension":["js"],"package":"./package.json","reporter":"spec","slow":"75","timeout":"5000","ui":"tdd","watch-files":["source/**/*.js","test/**/*.js"],"watch-ignore":["lib/vendor"]},"browser":{"./source/service/Fable-Service-EnvironmentData.js":"./source/service/Fable-Service-EnvironmentData-Web.js","./source/service/Fable-Service-FilePersistence.js":"./source/service/Fable-Service-FilePersistence-Web.js"},"repository":{"type":"git","url":"https://github.com/stevenvelozo/fable.git"},"keywords":["entity","behavior"],"author":"Steven Velozo <steven@velozo.com> (http://velozo.com/)","license":"MIT","bugs":{"url":"https://github.com/stevenvelozo/fable/issues"},"homepage":"https://github.com/stevenvelozo/fable","devDependencies":{"quackage":"^1.0.50"},"dependencies":{"async.eachlimit":"^0.5.2","async.waterfall":"^0.5.2","big.js":"^7.0.1","cachetrax":"^1.0.4","cookie":"^1.0.2","data-arithmatic":"^1.0.7","dayjs":"^1.11.19","fable-log":"^3.0.16","fable-serviceproviderbase":"^3.0.17","fable-settings":"^3.0.14","fable-uuid":"^3.0.11","manyfest":"^1.0.44","simple-get":"^4.0.1"}};},{}],150:[function(require,module,exports){/**
|
|
3192
3195
|
* Fable Application Services Support Library
|
|
3193
3196
|
* @author <steven@velozo.com>
|
|
3194
3197
|
*/// Pre-init services
|
|
@@ -3964,7 +3967,7 @@ tmpCurrentTokenType='Value';tmpCurrentToken+=tmpCharacter;// continue;
|
|
|
3964
3967
|
// tmpResults.ExpressionParserLog.push(`ExpressionParser.tokenize found an unknown character code ${tmpCharCode} character ${tmpCharacter} in the expression: ${pExpression} at index ${i}`);
|
|
3965
3968
|
// this.log.warn(tmpResults.ExpressionParserLog[tmpResults.ExpressionParserLog.length-1]);
|
|
3966
3969
|
}if(tmpCurrentTokenType&&tmpCurrentToken.length>0){tmpResults.RawTokens.push(tmpCurrentToken);}tmpResults.OriginalRawTokens=Array.from(tmpResults.RawTokens);// Potentially mutate the tokens based on directives in the tokenized expression
|
|
3967
|
-
this.TokenizerDirectiveMutation.parseDirectives(tmpResults);return tmpResults.RawTokens;}}module.exports=ExpressionTokenizer;},{"./Fable-Service-ExpressionParser-Base.js":159}],162:[function(require,module,exports){module.exports={"sqrt":{"Name":"Square Root","Address":"fable.Math.sqrtPrecise"},"percent":{"Name":"Compute Percent (in IS over OF format)","Address":"fable.Math.percentagePrecise"},"compare":{"Name":"Compare","Address":"fable.Math.comparePrecise"},"abs":{"Name":"Absolute Value","Address":"fable.Math.absPrecise"},"floor":{"Name":"Floor Value","Address":"fable.Math.floorPrecise"},"ceil":{"Name":"Ceiling Value","Address":"fable.Math.ceilPrecise"},"rad":{"Name":"Degrees to Radians","Address":"fable.Math.radPrecise"},"pi":{"Name":"Pi","Address":"fable.Math.piPrecise"},"euler":{"Name":"Euler","Address":"fable.Math.eulerPrecise"},"log":{"Name":"Logarithm","Address":"fable.Math.logPrecise"},"exp":{"Name":"Eulers Number to the Power Of N","Address":"fable.Math.expPrecise"},"sin":{"Name":"Sine","Address":"fable.Math.sin"},"cos":{"Name":"Cosine","Address":"fable.Math.cos"},"tan":{"Name":"Tangent","Address":"fable.Math.tan"},"count":{"Name":"Count Set Elements","Address":"fable.Math.countSetElements"},"countset":{"Name":"Count Set Elements","Address":"fable.Math.countSetElements"},"sortset":{"Name":"Sort Set","Address":"fable.Math.sortSetPrecise"},"bucketset":{"Name":"Bucket Set","Address":"fable.Math.bucketSetPrecise"},"sorthistogram":{"Name":"Sort Histogram","Address":"fable.Math.sortHistogramPrecise"},"sorthistogrambykeys":{"Name":"Sort Histogram by Keys","Address":"fable.Math.sortHistogramByKeys"},"max":{"Name":"Maximum","Address":"fable.Math.maxPrecise"},"min":{"Name":"Minimum","Address":"fable.Math.minPrecise"},"sum":{"Name":"Sum","Address":"fable.Math.sumPrecise"},"avg":{"Name":"Average","Address":"fable.Math.averagePrecise"},"mean":{"Name":"Mean","Address":"fable.Math.meanPrecise"},"median":{"Name":"Median","Address":"fable.Math.medianPrecise"},"mode":{"Name":"Mode","Address":"fable.Math.modePrecise"},"var":{"Name":"Variance (Sample)","Address":"fable.Math.variancePrecise"},"vara":{"Name":"Variance (Sample)","Address":"fable.Math.variancePrecise"},"varp":{"Name":"Variance (Population)","Address":"fable.Math.populationVariancePrecise"},"stdev":{"Name":"Standard Deviation (Sample)","Address":"fable.Math.standardDeviationPrecise"},"stdeva":{"Name":"Standard Deviation (Sample)","Address":"fable.Math.standardDeviationPrecise"},"stdevp":{"Name":"Standard Deviation (Population)","Address":"fable.Math.populationStandardDeviationPrecise"},"round":{"Name":"Round","Address":"fable.Math.roundPrecise"},"tofixed":{"Name":"To Fixed","Address":"fable.Math.toFixedPrecise"},"cumulativesummation":{"Name":"Sum each value in a Histogram or Value Map cumulatively, creating or setting a property with the result on each row","Address":"fable.Math.cumulativeSummation"},"subtractingsummation":{"Name":"Subtract each subsequent value in a Histogram or Value Map cumulatively (by default from the first row), creating or setting a property with the result on each row.","Address":"fable.Math.subtractingSummation"},"iterativeseries":{"Name":"Perform an Iterative Series of Mathematical Operations on Set Elements","Address":"fable.Math.iterativeSeries"},"countsetelements":{"Name":"Count Set Elements in a Histogram or Value Map","Address":"fable.Math.countSetElements"},"getvalue":{"Name":"Get Value from Application State or Services (AppData, etc.)","Address":"fable.Utility.getInternalValueByHash"},"objectkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"objectvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"generatearrayofobjectsfromsets":{"Name":"Generate Array of Objects from Sets","Address":"fable.Utility.generateArrayOfObjectsFromSets"},"objectvaluessortbyexternalobjectarray":{"Name":"Get Array of an Object's values sorted by an external array","Address":"fable.Utility.objectValuesSortByExternalArray"},"setkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"setvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"histogramkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"histogramvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"createarrayfromabsolutevalues":{"Name":"Create Array from Absolute Values","Address":"fable.Utility.createArrayFromAbsoluteValues"},"flatten":{"Name":"flatten an array of values","Address":"fable.Utility.flattenArrayOfSolverInputs"},"findfirstvaluebyexactmatch":{"Name":"find + map on array of objects","Address":"fable.Utility.findFirstValueByExactMatchInternal"},"findfirstvaluebystringincludes":{"Name":"find + map on array of objects","Address":"fable.Utility.findFirstValueByStringIncludesInternal"},"match":{"Name":"Implementation of sheets MATCH() function","Address":"fable.Utility.findIndexInternal"},"resolvehtmlentities":{"Name":"resolve HTML entities","Address":"fable.DataFormat.resolveHtmlEntities"},"concat":{"Name":"concatenate an array of values and output a string","Address":"fable.DataFormat.concatenateStringsInternal"},"concatraw":{"Name":"concatenate an array of values and output a string","Address":"fable.DataFormat.concatenateStringsRawInternal"},"arrayconcat":{"Name":"concatenate two or more arrays generating a single output array","Address":"fable.Utility.concatenateArrays"},"join":{"Name":"join an array of values and output a string","Address":"fable.DataFormat.joinStringsInternal"},"joinraw":{"Name":"join an array of values and output a string","Address":"fable.DataFormat.joinStringsRawInternal"},"if":{"Name":"perform a conditional operator on two values, and choose one of two outcomes based on the result","Address":"fable.Logic.checkIf"},"when":{"Name":"perform a 'truthy' check on one value, and return one of two outcomes based on the result","Address":"fable.Logic.when"},"entryinset":{"Name":"Entry in Set","Address":"fable.Math.entryInSet"},"smallestinset":{"Name":"Smallest in Set","Address":"fable.Math.smallestInSet"},"largestinset":{"Name":"Largest in Set","Address":"fable.Math.largestInSet"},"aggregationhistogram":{"Name":"Generate a Histogram by Exact Value Aggregation","Address":"fable.Math.histogramAggregationByExactValueFromInternalState"},"aggregationhistogrambyobject":{"Name":"Generate a Histogram by Exact Value Aggregation from Object Property","Address":"fable.Math.histogramAggregationByExactValue"},"distributionhistogram":{"Name":"Generate a Histogram Based on Value Distribution","Address":"fable.Math.histogramDistributionByExactValueFromInternalState"},"distributionhistogrambyobject":{"Name":"Generate a Histogram Based on Value Distribution from Object Property","Address":"fable.Math.histogramDistributionByExactValue"},"setconcatenate":{"Name":"Set Concatenate","Address":"fable.Math.setConcatenate"},"getvaluearray":{"Name":"Get Value Array from Application State or Services (AppData, etc.)","Address":"fable.Utility.createValueArrayByHashParametersFromInternal"},"getvalueobject":{"Name":"Get Value Object from Application State or Services (AppData, etc.)","Address":"fable.Utility.createValueObjectByHashParametersFromInternal"},"cleanvaluearray":{"Name":"Clean Value Array","Address":"fable.Math.cleanValueArray"},"cleanvalueobject":{"Name":"Clean Value Object","Address":"fable.Math.cleanValueObject"},"polynomialregression":{"Name":"Perform an nth degree Polynomial Regression on a Set of X and Y Values","Address":"fable.Math.polynomialRegression"},"randominteger":{"Name":"Random Integer","Address":"fable.DataGeneration.randomInteger"},"randomintegerbetween":{"Name":"Random Integer Between Two Numbers","Address":"fable.DataGeneration.randomIntegerBetween"},"randomintegerupto":{"Name":"Random Integer","Address":"fable.DataGeneration.randomIntegerUpTo"},"randomfloat":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloat"},"randomfloatbetween":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloatBetween"},"randomfloatupto":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloatUpTo"},"datemilliseconddifference":{"Name":"Date Difference in Milliseconds","Address":"fable.Dates.dateMillisecondDifference"},"dateseconddifference":{"Name":"Date Difference in Seconds","Address":"fable.Dates.dateSecondDifference"},"dateminutedifference":{"Name":"Date Difference in Minutes","Address":"fable.Dates.dateMinuteDifference"},"datehourdifference":{"Name":"Date Difference in Hours","Address":"fable.Dates.dateHourDifference"},"datedaydifference":{"Name":"Date Difference in Days","Address":"fable.Dates.dateDayDifference"},"dateweekdifference":{"Name":"Date Difference in Weeks","Address":"fable.Dates.dateWeekDifference"},"datemonthdifference":{"Name":"Date Difference in Months","Address":"fable.Dates.dateMonthDifference"},"dateyeardifference":{"Name":"Date Difference in Years","Address":"fable.Dates.dateYearDifference"},"datemathadd":{"Name":"Date Math Add","Address":"fable.Dates.dateMath"},"dateaddmilliseconds":{"Name":"Date Add Milliseconds","Address":"fable.Dates.dateAddMilliseconds"},"dateaddseconds":{"Name":"Date Add Seconds","Address":"fable.Dates.dateAddSeconds"},"dateaddminutes":{"Name":"Date Add Minutes","Address":"fable.Dates.dateAddMinutes"},"dateaddhours":{"Name":"Date Add Hours","Address":"fable.Dates.dateAddHours"},"dateadddays":{"Name":"Date Add Days","Address":"fable.Dates.dateAddDays"},"dateaddweeks":{"Name":"Date Add Weeks","Address":"fable.Dates.dateAddWeeks"},"dateaddmonths":{"Name":"Date Add Months","Address":"fable.Dates.dateAddMonths"},"dateaddyears":{"Name":"Date Add Years","Address":"fable.Dates.dateAddYears"},"datefromparts":{"Name":"Date From Parts","Address":"fable.Dates.dateFromParts"},"slice":{"Name":"Slice Array","Address":"fable.Utility.slice"},"createvalueobjectbyhashes":{"Name":"Create Value Object by Hashes","Address":"fable.Utility.createValueObjectByHashes"},"polynomialregression":{"Name":"Perform an nth degree Polynomial Regression on a Set of X and Y Values","Address":"fable.Math.polynomialRegression"},"leastsquares":{"Name":"Perform a Least Squares Regression on a Set of Independent Variable Vectors and a Dependent Variable Vector","Address":"fable.Math.leastSquares"},"linest":{"Name":"Perform a Least Squares Regression on a Set of Independent Variable Vectors and a Dependent Variable Vector","Address":"fable.Math.leastSquares"},"matrixtranspose":{"Name":"Transpose a Matrix","Address":"fable.Math.matrixTranspose"},"matrixmultiply":{"Name":"Multiply Two Matrices","Address":"fable.Math.matrixMultiply"},"matrixvectormultiply":{"Name":"Multiply a Matrix by a Vector","Address":"fable.Math.matrixVectorMultiply"},"matrixinverse":{"Name":"Inverse a Matrix","Address":"fable.Math.matrixInverse"},"gaussianelimination":{"Name":"Solve a System of Linear Equations using Gaussian Elimination","Address":"fable.Math.gaussianElimination"},"predict":{"Name":"Predict Y Values from X Values using a Regression Model","Address":"fable.Math.predictFromRegressionModel"},"stringcountsegments":{"Name":"Count Segments in a String","Address":"fable.DataFormat.stringCountSegments"},"stringgetsegments":{"Name":"Get Segments from a String","Address":"fable.DataFormat.stringGetSegments"}};},{}],163:[function(require,module,exports){const libExpressionParserOperationBase=require('./Fable-Service-ExpressionParser-Base.js');class ExpressionParserLinter extends libExpressionParserOperationBase{constructor(pFable,pOptions,pServiceHash){super(pFable,pOptions,pServiceHash);this.serviceType='ExpressionParser-Linter';}lintTokenizedExpression(pTokenizedExpression,pResultObject){let tmpResults=typeof pResultObject==='object'?pResultObject:{ExpressionParserLog:[]};tmpResults.LinterResults=[];// Guard against bad data being passed in
|
|
3970
|
+
this.TokenizerDirectiveMutation.parseDirectives(tmpResults);return tmpResults.RawTokens;}}module.exports=ExpressionTokenizer;},{"./Fable-Service-ExpressionParser-Base.js":159}],162:[function(require,module,exports){module.exports={"sqrt":{"Name":"Square Root","Address":"fable.Math.sqrtPrecise"},"percent":{"Name":"Compute Percent (in IS over OF format)","Address":"fable.Math.percentagePrecise"},"compare":{"Name":"Compare","Address":"fable.Math.comparePrecise"},"abs":{"Name":"Absolute Value","Address":"fable.Math.absPrecise"},"floor":{"Name":"Floor Value","Address":"fable.Math.floorPrecise"},"ceil":{"Name":"Ceiling Value","Address":"fable.Math.ceilPrecise"},"rad":{"Name":"Degrees to Radians","Address":"fable.Math.radPrecise"},"pi":{"Name":"Pi","Address":"fable.Math.piPrecise"},"euler":{"Name":"Euler","Address":"fable.Math.eulerPrecise"},"log":{"Name":"Logarithm","Address":"fable.Math.logPrecise"},"exp":{"Name":"Eulers Number to the Power Of N","Address":"fable.Math.expPrecise"},"sin":{"Name":"Sine","Address":"fable.Math.sin"},"cos":{"Name":"Cosine","Address":"fable.Math.cos"},"tan":{"Name":"Tangent","Address":"fable.Math.tan"},"count":{"Name":"Count Set Elements","Address":"fable.Math.countSetElements"},"countset":{"Name":"Count Set Elements","Address":"fable.Math.countSetElements"},"sortset":{"Name":"Sort Set","Address":"fable.Math.sortSetPrecise"},"bucketset":{"Name":"Bucket Set","Address":"fable.Math.bucketSetPrecise"},"sorthistogram":{"Name":"Sort Histogram","Address":"fable.Math.sortHistogramPrecise"},"sorthistogrambykeys":{"Name":"Sort Histogram by Keys","Address":"fable.Math.sortHistogramByKeys"},"max":{"Name":"Maximum","Address":"fable.Math.maxPrecise"},"min":{"Name":"Minimum","Address":"fable.Math.minPrecise"},"sum":{"Name":"Sum","Address":"fable.Math.sumPrecise"},"avg":{"Name":"Average","Address":"fable.Math.averagePrecise"},"mean":{"Name":"Mean","Address":"fable.Math.meanPrecise"},"median":{"Name":"Median","Address":"fable.Math.medianPrecise"},"mode":{"Name":"Mode","Address":"fable.Math.modePrecise"},"var":{"Name":"Variance (Sample)","Address":"fable.Math.variancePrecise"},"vara":{"Name":"Variance (Sample)","Address":"fable.Math.variancePrecise"},"varp":{"Name":"Variance (Population)","Address":"fable.Math.populationVariancePrecise"},"stdev":{"Name":"Standard Deviation (Sample)","Address":"fable.Math.standardDeviationPrecise"},"stdeva":{"Name":"Standard Deviation (Sample)","Address":"fable.Math.standardDeviationPrecise"},"stdevp":{"Name":"Standard Deviation (Population)","Address":"fable.Math.populationStandardDeviationPrecise"},"round":{"Name":"Round","Address":"fable.Math.roundPrecise"},"tofixed":{"Name":"To Fixed","Address":"fable.Math.toFixedPrecise"},"cumulativesummation":{"Name":"Sum each value in a Histogram or Value Map cumulatively, creating or setting a property with the result on each row","Address":"fable.Math.cumulativeSummation"},"subtractingsummation":{"Name":"Subtract each subsequent value in a Histogram or Value Map cumulatively (by default from the first row), creating or setting a property with the result on each row.","Address":"fable.Math.subtractingSummation"},"iterativeseries":{"Name":"Perform an Iterative Series of Mathematical Operations on Set Elements","Address":"fable.Math.iterativeSeries"},"countsetelements":{"Name":"Count Set Elements in a Histogram or Value Map","Address":"fable.Math.countSetElements"},"getvalue":{"Name":"Get Value from Application State or Services (AppData, etc.)","Address":"fable.Utility.getInternalValueByHash"},"setvalue":{"Name":"Set Value to Application State or Services (AppData, etc.)","Address":"fable.Utility.setInternalValueByHash"},"objectkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"objectvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"generatearrayofobjectsfromsets":{"Name":"Generate Array of Objects from Sets","Address":"fable.Utility.generateArrayOfObjectsFromSets"},"objectvaluessortbyexternalobjectarray":{"Name":"Get Array of an Object's values sorted by an external array","Address":"fable.Utility.objectValuesSortByExternalArray"},"setkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"setvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"histogramkeystoarray":{"Name":"Get Array of an Object's keys","Address":"fable.Utility.objectKeysToArray"},"histogramvaluestoarray":{"Name":"Get Array of an Object's values","Address":"fable.Utility.objectValuesToArray"},"createarrayfromabsolutevalues":{"Name":"Create Array from Absolute Values","Address":"fable.Utility.createArrayFromAbsoluteValues"},"flatten":{"Name":"flatten an array of values","Address":"fable.Utility.flattenArrayOfSolverInputs"},"findfirstvaluebyexactmatch":{"Name":"find + map on array of objects","Address":"fable.Utility.findFirstValueByExactMatchInternal"},"findfirstvaluebystringincludes":{"Name":"find + map on array of objects","Address":"fable.Utility.findFirstValueByStringIncludesInternal"},"match":{"Name":"Implementation of sheets MATCH() function","Address":"fable.Utility.findIndexInternal"},"resolvehtmlentities":{"Name":"resolve HTML entities","Address":"fable.DataFormat.resolveHtmlEntities"},"concat":{"Name":"concatenate an array of values and output a string","Address":"fable.DataFormat.concatenateStringsInternal"},"concatraw":{"Name":"concatenate an array of values and output a string","Address":"fable.DataFormat.concatenateStringsRawInternal"},"arrayconcat":{"Name":"concatenate two or more arrays generating a single output array","Address":"fable.Utility.concatenateArrays"},"join":{"Name":"join an array of values and output a string","Address":"fable.DataFormat.joinStringsInternal"},"joinraw":{"Name":"join an array of values and output a string","Address":"fable.DataFormat.joinStringsRawInternal"},"if":{"Name":"perform a conditional operator on two values, and choose one of two outcomes based on the result","Address":"fable.Logic.checkIf"},"when":{"Name":"perform a 'truthy' check on one value, and return one of two outcomes based on the result","Address":"fable.Logic.when"},"entryinset":{"Name":"Entry in Set","Address":"fable.Math.entryInSet"},"smallestinset":{"Name":"Smallest in Set","Address":"fable.Math.smallestInSet"},"largestinset":{"Name":"Largest in Set","Address":"fable.Math.largestInSet"},"aggregationhistogram":{"Name":"Generate a Histogram by Exact Value Aggregation","Address":"fable.Math.histogramAggregationByExactValueFromInternalState"},"aggregationhistogrambyobject":{"Name":"Generate a Histogram by Exact Value Aggregation from Object Property","Address":"fable.Math.histogramAggregationByExactValue"},"distributionhistogram":{"Name":"Generate a Histogram Based on Value Distribution","Address":"fable.Math.histogramDistributionByExactValueFromInternalState"},"distributionhistogrambyobject":{"Name":"Generate a Histogram Based on Value Distribution from Object Property","Address":"fable.Math.histogramDistributionByExactValue"},"setconcatenate":{"Name":"Set Concatenate","Address":"fable.Math.setConcatenate"},"getvaluearray":{"Name":"Get Value Array from Application State or Services (AppData, etc.)","Address":"fable.Utility.createValueArrayByHashParametersFromInternal"},"getvalueobject":{"Name":"Get Value Object from Application State or Services (AppData, etc.)","Address":"fable.Utility.createValueObjectByHashParametersFromInternal"},"cleanvaluearray":{"Name":"Clean Value Array","Address":"fable.Math.cleanValueArray"},"cleanvalueobject":{"Name":"Clean Value Object","Address":"fable.Math.cleanValueObject"},"polynomialregression":{"Name":"Perform an nth degree Polynomial Regression on a Set of X and Y Values","Address":"fable.Math.polynomialRegression"},"randominteger":{"Name":"Random Integer","Address":"fable.DataGeneration.randomInteger"},"randomintegerbetween":{"Name":"Random Integer Between Two Numbers","Address":"fable.DataGeneration.randomIntegerBetween"},"randomintegerupto":{"Name":"Random Integer","Address":"fable.DataGeneration.randomIntegerUpTo"},"randomfloat":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloat"},"randomfloatbetween":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloatBetween"},"randomfloatupto":{"Name":"Random Float","Address":"fable.DataGeneration.randomFloatUpTo"},"datemilliseconddifference":{"Name":"Date Difference in Milliseconds","Address":"fable.Dates.dateMillisecondDifference"},"dateseconddifference":{"Name":"Date Difference in Seconds","Address":"fable.Dates.dateSecondDifference"},"dateminutedifference":{"Name":"Date Difference in Minutes","Address":"fable.Dates.dateMinuteDifference"},"datehourdifference":{"Name":"Date Difference in Hours","Address":"fable.Dates.dateHourDifference"},"datedaydifference":{"Name":"Date Difference in Days","Address":"fable.Dates.dateDayDifference"},"dateweekdifference":{"Name":"Date Difference in Weeks","Address":"fable.Dates.dateWeekDifference"},"datemonthdifference":{"Name":"Date Difference in Months","Address":"fable.Dates.dateMonthDifference"},"dateyeardifference":{"Name":"Date Difference in Years","Address":"fable.Dates.dateYearDifference"},"datemathadd":{"Name":"Date Math Add","Address":"fable.Dates.dateMath"},"dateaddmilliseconds":{"Name":"Date Add Milliseconds","Address":"fable.Dates.dateAddMilliseconds"},"dateaddseconds":{"Name":"Date Add Seconds","Address":"fable.Dates.dateAddSeconds"},"dateaddminutes":{"Name":"Date Add Minutes","Address":"fable.Dates.dateAddMinutes"},"dateaddhours":{"Name":"Date Add Hours","Address":"fable.Dates.dateAddHours"},"dateadddays":{"Name":"Date Add Days","Address":"fable.Dates.dateAddDays"},"dateaddweeks":{"Name":"Date Add Weeks","Address":"fable.Dates.dateAddWeeks"},"dateaddmonths":{"Name":"Date Add Months","Address":"fable.Dates.dateAddMonths"},"dateaddyears":{"Name":"Date Add Years","Address":"fable.Dates.dateAddYears"},"datefromparts":{"Name":"Date From Parts","Address":"fable.Dates.dateFromParts"},"slice":{"Name":"Slice Array","Address":"fable.Utility.slice"},"createvalueobjectbyhashes":{"Name":"Create Value Object by Hashes","Address":"fable.Utility.createValueObjectByHashes"},"polynomialregression":{"Name":"Perform an nth degree Polynomial Regression on a Set of X and Y Values","Address":"fable.Math.polynomialRegression"},"leastsquares":{"Name":"Perform a Least Squares Regression on a Set of Independent Variable Vectors and a Dependent Variable Vector","Address":"fable.Math.leastSquares"},"linest":{"Name":"Perform a Least Squares Regression on a Set of Independent Variable Vectors and a Dependent Variable Vector","Address":"fable.Math.leastSquares"},"matrixtranspose":{"Name":"Transpose a Matrix","Address":"fable.Math.matrixTranspose"},"matrixmultiply":{"Name":"Multiply Two Matrices","Address":"fable.Math.matrixMultiply"},"matrixvectormultiply":{"Name":"Multiply a Matrix by a Vector","Address":"fable.Math.matrixVectorMultiply"},"matrixinverse":{"Name":"Inverse a Matrix","Address":"fable.Math.matrixInverse"},"gaussianelimination":{"Name":"Solve a System of Linear Equations using Gaussian Elimination","Address":"fable.Math.gaussianElimination"},"predict":{"Name":"Predict Y Values from X Values using a Regression Model","Address":"fable.Math.predictFromRegressionModel"},"stringcountsegments":{"Name":"Count Segments in a String","Address":"fable.DataFormat.stringCountSegments"},"stringgetsegments":{"Name":"Get Segments from a String","Address":"fable.DataFormat.stringGetSegments"}};},{}],163:[function(require,module,exports){const libExpressionParserOperationBase=require('./Fable-Service-ExpressionParser-Base.js');class ExpressionParserLinter extends libExpressionParserOperationBase{constructor(pFable,pOptions,pServiceHash){super(pFable,pOptions,pServiceHash);this.serviceType='ExpressionParser-Linter';}lintTokenizedExpression(pTokenizedExpression,pResultObject){let tmpResults=typeof pResultObject==='object'?pResultObject:{ExpressionParserLog:[]};tmpResults.LinterResults=[];// Guard against bad data being passed in
|
|
3968
3971
|
if(!Array.isArray(pTokenizedExpression)){tmpResults.ExpressionParserLog.push(`ERROR: ExpressionParser.lintTokenizedExpression was passed a non-array tokenized expression.`);tmpResults.LinterResults.push(tmpResults.ExpressionParserLog[tmpResults.ExpressionParserLog.length-1]);this.log.error(tmpResults.ExpressionParserLog[tmpResults.ExpressionParserLog.length-1]);return pTokenizedExpression;}if(pTokenizedExpression.length<1){tmpResults.ExpressionParserLog.push(`ERROR: ExpressionParser.lintTokenizedExpression was passed an empty tokenized expression.`);tmpResults.LinterResults.push(tmpResults.ExpressionParserLog[tmpResults.ExpressionParserLog.length-1]);this.log.error(tmpResults.ExpressionParserLog[tmpResults.ExpressionParserLog.length-1]);return pTokenizedExpression;}// 1. Check for balanced parenthesis
|
|
3969
3972
|
let tmpParenthesisDepth=0;// If it is in a state address, we don't care about the parenthesis
|
|
3970
3973
|
// State addresses are between squiggly brackets
|
|
@@ -4940,6 +4943,12 @@ let tmpChunkSize=typeof pChunkSize=='number'?pChunkSize:0;let tmpChunkCache=type
|
|
|
4940
4943
|
* @param {string} pValueAddress - The manyfest hash/address of the value to get
|
|
4941
4944
|
*/getInternalValueByHash(pValueAddress){// Get the value from the internal manifest and return it
|
|
4942
4945
|
return this.getValueByHash(this.fable,pValueAddress);}/**
|
|
4946
|
+
* Set a value from fable/pict by hash/address
|
|
4947
|
+
*
|
|
4948
|
+
* @param {string} pValueAddress - The manyfest hash/address of the value to get
|
|
4949
|
+
* @param {any} pValue - The value to set
|
|
4950
|
+
*/setInternalValueByHash(pValueAddress,pValue){// Get the value from the internal manifest and return it
|
|
4951
|
+
return this.setValueByHash(this.fable,pValueAddress,pValue);}/**
|
|
4943
4952
|
* Get a value from an object by hash/address
|
|
4944
4953
|
* @param {object} pObject - The object to get the value from
|
|
4945
4954
|
* @param {string} pValueAddress - The manyfest hash/address of the value to get
|