mirror of
https://github.com/Hopiu/webapi-eca.git
synced 2026-03-16 22:10:31 +00:00
action invokers can also push events back into the system now. Neospeech example works.
This commit is contained in:
parent
b1e4fc9af5
commit
f013f6fb93
20 changed files with 279 additions and 94 deletions
|
|
@ -62,8 +62,11 @@ exports.addRuleListener = ( eh ) =>
|
|||
try
|
||||
oRule = JSON.parse strRule
|
||||
db.resetLog userName, oRule.id
|
||||
db.appendLog userName, oRule.id, "INIT", "Rule '#{ oRule.id }' initialized.
|
||||
Interval set to #{ oRule.event_interval } minutes"
|
||||
|
||||
eventInfo = ''
|
||||
if oRule.event_start
|
||||
eventInfo = "Starting at #{ new Date( oRule.event_start ) }, Interval set to #{ oRule.event_interval } minutes"
|
||||
db.appendLog userName, oRule.id, "INIT", "Rule '#{ oRule.id }' initialized. #{ eventInfo }"
|
||||
|
||||
eventEmitter.emit 'rule',
|
||||
event: 'init'
|
||||
|
|
@ -187,13 +190,13 @@ getModuleUserArguments = ( user, oPayload, dbMod, callback ) ->
|
|||
answ.message = oPayload
|
||||
callback answ
|
||||
|
||||
forgeModule = ( user, oPayload, dbMod, callback ) =>
|
||||
forgeModule = ( user, oPayload, modType, dbMod, callback ) =>
|
||||
answ = hasRequiredParams [ 'id', 'params', 'lang', 'data' ], oPayload
|
||||
if answ.code isnt 200
|
||||
callback answ
|
||||
else
|
||||
if oPayload.overwrite
|
||||
storeModule user, oPayload, dbMod, callback
|
||||
storeModule user, oPayload, modType, dbMod, callback
|
||||
else
|
||||
dbMod.getModule user.username, oPayload.id, ( err, mod ) =>
|
||||
if mod
|
||||
|
|
@ -201,11 +204,11 @@ forgeModule = ( user, oPayload, dbMod, callback ) =>
|
|||
answ.message = 'Module name already existing: ' + oPayload.id
|
||||
callback answ
|
||||
else
|
||||
storeModule user, oPayload, dbMod, callback
|
||||
storeModule user, oPayload, modType, dbMod, callback
|
||||
|
||||
storeModule = ( user, oPayload, dbMod, callback ) =>
|
||||
storeModule = ( user, oPayload, modType, dbMod, callback ) =>
|
||||
src = oPayload.data
|
||||
dynmod.compileString src, user.username, 'dummyRule', oPayload.id, oPayload.lang, null, ( cm ) =>
|
||||
dynmod.compileString src, user.username, id: 'dummyRule' , oPayload.id, oPayload.lang, modType, null, ( cm ) =>
|
||||
answ = cm.answ
|
||||
if answ.code is 200
|
||||
funcs = []
|
||||
|
|
@ -311,7 +314,7 @@ commandFunctions =
|
|||
message: obj
|
||||
|
||||
forge_event_poller: ( user, oPayload, callback ) ->
|
||||
forgeModule user, oPayload, db.eventPollers, callback
|
||||
forgeModule user, oPayload, "eventpoller", db.eventPollers, callback
|
||||
|
||||
delete_event_poller: ( user, oPayload, callback ) ->
|
||||
answ = hasRequiredParams [ 'id' ], oPayload
|
||||
|
|
@ -358,7 +361,7 @@ commandFunctions =
|
|||
message: obj
|
||||
|
||||
forge_action_invoker: ( user, oPayload, callback ) ->
|
||||
forgeModule user, oPayload, db.actionInvokers, callback
|
||||
forgeModule user, oPayload, "actioninvoker", db.actionInvokers, callback
|
||||
|
||||
delete_action_invoker: ( user, oPayload, callback ) ->
|
||||
answ = hasRequiredParams [ 'id' ], oPayload
|
||||
|
|
|
|||
|
|
@ -27,7 +27,6 @@ cryptoJS = require 'crypto-js'
|
|||
importio = require( 'import-io' ).client
|
||||
|
||||
|
||||
|
||||
###
|
||||
Module call
|
||||
-----------
|
||||
|
|
@ -63,7 +62,7 @@ compile it first into JS.
|
|||
@param {Object} params
|
||||
@param {String} lang
|
||||
###
|
||||
exports.compileString = ( src, userId, ruleId, modId, lang, dbMod, cb ) =>
|
||||
exports.compileString = ( src, userId, oRule, modId, lang, modType, dbMod, cb ) =>
|
||||
if lang is 'CoffeeScript'
|
||||
try
|
||||
@log.info "DM | Compiling module '#{ modId }' for user '#{ userId }'"
|
||||
|
|
@ -84,16 +83,30 @@ exports.compileString = ( src, userId, ruleId, modId, lang, dbMod, cb ) =>
|
|||
oParams = {}
|
||||
for name, oParam of JSON.parse obj
|
||||
oParams[ name ] = encryption.decrypt oParam.value
|
||||
@log.info "DM | Loaded user defined params for #{ userId }, #{ ruleId }, #{ modId }"
|
||||
@log.info "DM | Loaded user defined params for #{ userId }, #{ oRule.id }, #{ modId }"
|
||||
catch err
|
||||
@log.warn "DM | Error during parsing of user defined params for #{ userId }, #{ ruleId }, #{ modId }"
|
||||
@log.warn "DM | Error during parsing of user defined params for #{ userId }, #{ oRule.id }, #{ modId }"
|
||||
@log.warn err
|
||||
fTryToLoadModule userId, ruleId, modId, src, dbMod, oParams, cb
|
||||
fTryToLoadModule userId, oRule, modId, src, modType, dbMod, oParams, cb
|
||||
else
|
||||
fTryToLoadModule userId, ruleId, modId, src, dbMod, null, cb
|
||||
fTryToLoadModule userId, oRule, modId, src, modType, dbMod, null, cb
|
||||
|
||||
|
||||
fTryToLoadModule = ( userId, ruleId, modId, src, dbMod, params, cb ) =>
|
||||
fPushEvent = ( userId, oRule, modType ) ->
|
||||
( obj ) ->
|
||||
timestamp = ( new Date() ).toISOString()
|
||||
rand = ( Math.floor Math.random() * 10e9 ).toString( 16 ).toUpperCase()
|
||||
if modType is 'eventpoller'
|
||||
db.pushEvent
|
||||
event: oRule.event + '_created:' + oRule.timestamp
|
||||
eventid: "#{ userId }_#{ oRule.event }_UTC|#{ timestamp }_#{ rand }"
|
||||
payload: obj
|
||||
|
||||
else
|
||||
obj.eventid = "#{ userId }_#{ oRule.event }_UTC|#{ timestamp }_#{ rand }"
|
||||
db.pushEvent obj
|
||||
|
||||
fTryToLoadModule = ( userId, oRule, modId, src, modType, dbMod, params, cb ) =>
|
||||
if not params
|
||||
params = {}
|
||||
|
||||
|
|
@ -103,10 +116,10 @@ fTryToLoadModule = ( userId, ruleId, modId, src, dbMod, params, cb ) =>
|
|||
|
||||
@log.info "DM | Running module '#{ modId }' for user '#{ userId }'"
|
||||
# The function used to provide logging mechanisms on a per rule basis
|
||||
logFunc = logFunction userId, ruleId, modId
|
||||
logFunc = logFunction userId, oRule.id, modId
|
||||
# The sandbox contains the objects that are accessible to the user. Eventually they need to be required from a vm themselves
|
||||
sandbox =
|
||||
id: "#{ userId }.#{ ruleId }.#{ modId }.vm"
|
||||
id: "#{ userId }.#{ oRule.id }.#{ modId }.vm"
|
||||
params: params
|
||||
needle: needle
|
||||
importio: importio
|
||||
|
|
@ -115,6 +128,8 @@ fTryToLoadModule = ( userId, ruleId, modId, src, dbMod, params, cb ) =>
|
|||
log: logFunc
|
||||
debug: console.log
|
||||
exports: {}
|
||||
pushEvent: fPushEvent userId, oRule, modType
|
||||
|
||||
|
||||
#TODO child_process to run module!
|
||||
#Define max runtime per function call as 10 seconds, after that the child will be killed
|
||||
|
|
@ -132,7 +147,7 @@ fTryToLoadModule = ( userId, ruleId, modId, src, dbMod, params, cb ) =>
|
|||
msg = 'Try to run the script locally to track the error! Sadly we cannot provide the line number'
|
||||
answ.message = 'Loading Module failed: ' + msg
|
||||
|
||||
@log.info "DM | Module '#{ modId }' ran successfully for user '#{ userId }' in rule '#{ ruleId }'"
|
||||
@log.info "DM | Module '#{ modId }' ran successfully for user '#{ userId }' in rule '#{ oRule.id }'"
|
||||
oFuncParams = {}
|
||||
oFuncArgs = {}
|
||||
for fName, func of sandbox.exports
|
||||
|
|
@ -146,12 +161,12 @@ fTryToLoadModule = ( userId, ruleId, modId, src, dbMod, params, cb ) =>
|
|||
if obj
|
||||
try
|
||||
oFuncArgs[ fName ] = JSON.parse obj
|
||||
@log.info "DM | Found and attached user-specific arguments to #{ userId }, #{ ruleId }, #{ modId }: #{ obj }"
|
||||
@log.info "DM | Found and attached user-specific arguments to #{ userId }, #{ oRule.id }, #{ modId }: #{ obj }"
|
||||
catch err
|
||||
@log.warn "DM | Error during parsing of user-specific arguments for #{ userId }, #{ ruleId }, #{ modId }"
|
||||
@log.warn "DM | Error during parsing of user-specific arguments for #{ userId }, #{ oRule.id }, #{ modId }"
|
||||
@log.warn err
|
||||
for func of oFuncParams
|
||||
dbMod.getUserArguments userId, ruleId, modId, func, fRegisterArguments func
|
||||
dbMod.getUserArguments userId, oRule.id, modId, func, fRegisterArguments func
|
||||
cb
|
||||
answ: answ
|
||||
module: sandbox.exports
|
||||
|
|
|
|||
|
|
@ -150,10 +150,11 @@ updateActionModules = ( updatedRuleId ) =>
|
|||
# we compile the module and pass:
|
||||
dynmod.compileString obj.data, # code
|
||||
userName, # userId
|
||||
oMyRule.rule.id, # ruleId
|
||||
oMyRule.rule, # oRule
|
||||
moduleName, # moduleId
|
||||
obj.lang, # script language
|
||||
db.actionInvokers, # the DB interface
|
||||
"actioninvoker", # module type
|
||||
db.actionInvokers, # the DB interface
|
||||
( result ) =>
|
||||
if result.answ.code is 200
|
||||
@log.info "EN | Module '#{ moduleName }' successfully loaded for userName
|
||||
|
|
@ -245,12 +246,13 @@ processEvent = ( evt ) =>
|
|||
for oArg in node.funcArgs[ funcName ]
|
||||
arrSelectors = oArg.value.match /#\{(.*?)\}/g
|
||||
argument = oArg.value
|
||||
for sel in arrSelectors
|
||||
selector = sel.substring 2, sel.length - 1
|
||||
data = jsonQuery( evt.payload, selector ).nodes()[ 0 ]
|
||||
argument = argument.replace sel, data
|
||||
if oArg.value is sel
|
||||
argument = data # if the user wants to pass an object, we allow him to do so
|
||||
if arrSelectors
|
||||
for sel in arrSelectors
|
||||
selector = sel.substring 2, sel.length - 1
|
||||
data = jsonQuery( evt.payload, selector ).nodes()[ 0 ]
|
||||
argument = argument.replace sel, data
|
||||
if oArg.value is sel
|
||||
argument = data # if the user wants to pass an object, we allow him to do so
|
||||
# if oArg.jsselector
|
||||
arrArgs.push argument #jsonQuery( evt.payload, oArg.value ).nodes()[ 0 ]
|
||||
# else
|
||||
|
|
|
|||
|
|
@ -82,9 +82,10 @@ fLoadModule = ( msg ) ->
|
|||
# we compile the module and pass:
|
||||
dynmod.compileString obj.data, # code
|
||||
msg.user, # userId
|
||||
msg.rule.id, # ruleId
|
||||
msg.rule, # oRule
|
||||
arrName[0], # moduleId
|
||||
obj.lang, # script language
|
||||
"eventpoller", # the module type
|
||||
db.eventPollers, # the DB interface
|
||||
( result ) ->
|
||||
if not result.answ is 200
|
||||
|
|
@ -105,7 +106,6 @@ fLoadModule = ( msg ) ->
|
|||
event_interval: msg.rule.event_interval * 60 * 1000
|
||||
module: result.module
|
||||
logger: result.logger
|
||||
oUser[msg.rule.id].module.pushEvent = fPushEvent msg.user, msg.rule.id, oUser[msg.rule.id]
|
||||
|
||||
start = new Date msg.rule.event_start
|
||||
nd = new Date()
|
||||
|
|
@ -133,12 +133,6 @@ fLoadModule = ( msg ) ->
|
|||
not listUserModules[msg.user][msg.rule.id]
|
||||
fAnonymous()
|
||||
|
||||
fPushEvent = ( userId, ruleId, oRule ) ->
|
||||
( obj ) ->
|
||||
db.pushEvent
|
||||
event: oRule.id + '_created:' + oRule.timestamp
|
||||
eventid: "polled #{ oRule.id } #{ userId }_UTC|#{ ( new Date() ).toISOString() }"
|
||||
payload: obj
|
||||
fCheckAndRun = ( userId, ruleId, timestamp ) ->
|
||||
() ->
|
||||
log.info "EP | Check and run user #{ userId }, rule #{ ruleId }"
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
{
|
||||
"http-port": 8125,
|
||||
"db-port": 6379,
|
||||
"db-select": 1,
|
||||
"db-select": 0,
|
||||
"log": {
|
||||
"nolog": "false",
|
||||
"mode": "productive",
|
||||
|
|
|
|||
6
examples/TODO
Normal file
6
examples/TODO
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
TODO's webservices
|
||||
|
||||
Google: (OAuth)
|
||||
https://developers.google.com/accounts/docs/OAuth2WebServer
|
||||
|
||||
Github Webhook
|
||||
|
|
@ -2,5 +2,5 @@
|
|||
# Pushes an event into the system each time the function is polled
|
||||
#
|
||||
exports.push = () ->
|
||||
exports.pushEvent
|
||||
pushEvent
|
||||
content: "This is an event that will be sent again and again every ten seconds"
|
||||
|
|
@ -23,7 +23,7 @@ exports.newMail = () ->
|
|||
if resp.statusCode is 200
|
||||
if body.Emails.length > 0
|
||||
log "#{ body.Emails.length } mail events pushed into the system"
|
||||
exports.pushEvent mail for mail in body.Emails
|
||||
pushEvent mail for mail in body.Emails
|
||||
|
||||
###
|
||||
This will emit events of the form:
|
||||
|
|
|
|||
|
|
@ -49,7 +49,7 @@ queryService = ( inputParams ) ->
|
|||
data = data.concat msg.data.results
|
||||
if finished
|
||||
log JSON.stringify data
|
||||
exports.pushEvent data
|
||||
pushEvent data
|
||||
|
||||
exports.meteoblueWeekData = ( idCity ) ->
|
||||
params =
|
||||
|
|
|
|||
111
examples/event-pollers/neospeech.coffee
Normal file
111
examples/event-pollers/neospeech.coffee
Normal file
|
|
@ -0,0 +1,111 @@
|
|||
# Neospeech
|
||||
#
|
||||
# Converts text to speech and issues an event into th system on completion
|
||||
#
|
||||
# Requires user-specific parameters:
|
||||
#
|
||||
# - emailaccount
|
||||
# - accountid
|
||||
# - loginkey
|
||||
# - loginpassword
|
||||
|
||||
arrVoices = [
|
||||
"TTS_KATE_DB"
|
||||
"TTS_PAUL_DB"
|
||||
"TTS_JULIE_DB"
|
||||
"TTS_NEOBRIDGET_DB"
|
||||
"TTS_NEOVIOLETA_DB"
|
||||
]
|
||||
|
||||
arrFormats = [
|
||||
"FORMAT_WAV" # (16bit linear PCM Wave)
|
||||
"FORMAT_PCM" # (16bit linear PCM)
|
||||
"FORMAT_MULAW" # (8bit Mu-law PCM)
|
||||
"FORMAT_ALAW" # (8bit A-law PCM)
|
||||
"FORMAT_ADPCM" # (4bit Dialogic ADPCM)
|
||||
"FORMAT_OGG" # (Ogg Vorbis)
|
||||
"FORMAT_8BITWAV" # (8bit unsigned linear PCM Wave)
|
||||
"FORMAT_AWAV" # (8bit A-law PCM Wave)
|
||||
"FORMAT_MUWAV" # (8bit Mu-law PCM Wave)
|
||||
]
|
||||
|
||||
# oResponseCodes =
|
||||
# "0": "success"
|
||||
# "-1": "invalid login"
|
||||
# "-2": "account inactive"
|
||||
# "-3": "account unauthorized"
|
||||
# "-4": "invalid or inactive login key"
|
||||
# "-5": "invalid conversion number lookup"
|
||||
# "-6": "content size is too large (only for “Basic” subscribers)"
|
||||
# "-7": "monthly allowance has been exceeded (only for “Basic” subscribers)"
|
||||
# "-10": "invalid TTS Voice ID"
|
||||
# "-11": "invalid TTS Output Format ID"
|
||||
# "-12": "invalid REST request"
|
||||
# "-13": "invalid or unavailable TTS Sample Rate"
|
||||
# "1": "invalid SSML (not a valid XML document)"
|
||||
# "2": "invalid SSML (SSML content must begin with a “speak” tag)"
|
||||
# "3": "invalid SSML (“lexicon” tag is not supported)"
|
||||
|
||||
parseAnswer = ( body ) ->
|
||||
arrSelectors = body.match /(\S+)=["']?((?:.(?!["']?\s+(?:\S+)=|[>"']))+.)["']?/g
|
||||
oAnswer = {}
|
||||
for sel in arrSelectors
|
||||
arrSel = sel.split '='
|
||||
oAnswer[ arrSel[ 0 ] ] = arrSel[ 1 ].substring 1, arrSel[ 1 ].length - 1
|
||||
oAnswer
|
||||
|
||||
# Function arguments:
|
||||
# - text: the text to be translated into voice
|
||||
# - idVoice: index of the voice used for conversion from the arrVoices array.
|
||||
# - idAudioFormat: index of the voice used for conversion from the arrVoices array.
|
||||
# - sampleRate: 8 or 16 kHz rate
|
||||
exports.convertTextToSpeech = ( text, idVoice, idAudioFormat, sampleRate ) ->
|
||||
idVoice = parseInt( idVoice ) || 0
|
||||
if idVoice > arrVoices.length - 1 or idVoice < 0
|
||||
idVoice = 0
|
||||
|
||||
idAudioFormat = parseInt( idAudioFormat ) || 0
|
||||
if idAudioFormat > arrFormats.length - 1 or idAudioFormat < 0
|
||||
idAudioFormat = 0
|
||||
|
||||
sampleRate = parseInt( sampleRate ) || 8
|
||||
if sampleRate isnt 8 or sampleRate isnt 16
|
||||
sampleRate = 8
|
||||
|
||||
oPost =
|
||||
method: "ConvertSimple"
|
||||
email: params.emailaccount
|
||||
accountId: params.accountid
|
||||
loginKey: params.loginkey
|
||||
loginPassword: params.loginpassword
|
||||
voice: arrVoices[ idVoice ]
|
||||
outputFormat: arrFormats[ idAudioFormat ]
|
||||
sampleRate: sampleRate
|
||||
text: text
|
||||
|
||||
needle.post "https://tts.neospeech.com/rest_1_1.php", oPost, ( err, resp, body ) ->
|
||||
oAnsw = parseAnswer body
|
||||
log 'Conversion order: ' + oAnsw.resultString
|
||||
if oAnsw.resultCode is '0'
|
||||
pollUntilDone oAnsw.resultCode, params.emailaccount, params.accountid
|
||||
|
||||
pollUntilDone = ( conversionNumber, email, accountid ) ->
|
||||
oPost =
|
||||
method: "GetConversionStatus"
|
||||
email: email
|
||||
accountId: accountid
|
||||
conversionNumber: conversionNumber
|
||||
|
||||
needle.post "https://tts.neospeech.com/rest_1_1.php", oPost, ( err, resp, body ) ->
|
||||
oAnsw = parseAnswer body
|
||||
if oAnsw.resultCode is '0'
|
||||
if oAnsw.statusCode is '4' or oAnsw.statusCode is '5'
|
||||
pushEvent
|
||||
event: "NeospeechConversionCompleted"
|
||||
payload:
|
||||
accountid: accountid
|
||||
downloadUrl: oAnsw.downloadUrl
|
||||
else
|
||||
pollUntilDone conversionNumber, email, accountid
|
||||
else
|
||||
log 'Request failed: ' + oAnsw.resultString
|
||||
|
|
@ -53,7 +53,7 @@ exports.unreadContentInfo = () ->
|
|||
method: 'unreadcontent'
|
||||
callback: ( err, resp, body ) ->
|
||||
if not err and resp.statusCode is 200
|
||||
exports.pushEvent oEntry for oEntry in body
|
||||
pushEvent oEntry for oEntry in body
|
||||
else
|
||||
log 'Error: ' + body.error.message
|
||||
|
||||
|
|
@ -67,7 +67,7 @@ exports.unreadContent = () ->
|
|||
contentServiceId: evt.serviceId
|
||||
callback: ( err, resp, body ) ->
|
||||
if not err and resp.statusCode is 200
|
||||
exports.pushEvent
|
||||
pushEvent
|
||||
id: body.id
|
||||
content: body.text
|
||||
object: body
|
||||
|
|
|
|||
43
examples/event-pollers/security.coffee
Normal file
43
examples/event-pollers/security.coffee
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
#
|
||||
# Security EVENT POLLER
|
||||
# ---------------------
|
||||
#
|
||||
# Informs about security breaches.
|
||||
#
|
||||
# Will emit events of the form:
|
||||
# [
|
||||
# {
|
||||
# "Title": "Adobe",
|
||||
# "Name": "Adobe",
|
||||
# "Domain": "adobe.com",
|
||||
# "BreachDate": "2013-10-4",
|
||||
# "AddedDate": "2013-12-4T00:12Z",
|
||||
# "PwnCount": 152445165,
|
||||
# "Description": "The big one. In October 2013, 153 million accounts were breached with each containing an internal ID, username, email, <em>encrypted</em> password and a password hint in plain text. The password cryptography was poorly done and <a href=\"http://stricture-group.com/files/adobe-top100.txt\"> many were quickly resolved back to plain text</a>. The unencrypted hints also <a href=\"http://www.troyhunt.com/2013/11/adobe-credentials-and-serious.html\">disclosed much about the passwords</a> adding further to the risk that hundreds of millions of Adobe customers already faced.",
|
||||
# "DataClasses": [
|
||||
# "Email addresses",
|
||||
# "Password hints",
|
||||
# "Passwords",
|
||||
# "Usernames"
|
||||
# ]
|
||||
# },
|
||||
# [...]
|
||||
# ]
|
||||
|
||||
oAccountBreaches = {}
|
||||
exports.breachedAccount = ( account ) ->
|
||||
needle.get "https://haveibeenpwned.com/api/v2/breachedaccount/#{ account }", ( err, resp, body ) ->
|
||||
for oBreach in body
|
||||
myId = oBreach.Title + "_" + oBreach.AddedDate
|
||||
if not oAccountBreaches[ myId ]
|
||||
oAccountBreaches[ myId ] = oBreach
|
||||
pushEvent oBreach
|
||||
|
||||
oBreaches = {}
|
||||
exports.newBreachedSite = () ->
|
||||
needle.get 'https://haveibeenpwned.com/api/v2/breaches', ( err, resp, body ) ->
|
||||
for oBreach in body
|
||||
myId = oBreach.Title + "_" + oBreach.AddedDate
|
||||
if not oBreaches[ myId ]
|
||||
oBreaches[ myId ] = oBreach
|
||||
pushEvent oBreach
|
||||
|
|
@ -11,6 +11,6 @@ This event is emitted if the system had a restart.
|
|||
exports.hasRestarted = () ->
|
||||
if not isRunning
|
||||
isRunning = true
|
||||
exports.pushEvent
|
||||
pushEvent
|
||||
content: "The system has been restarted at #{ ( new Date ).toISOString() }"
|
||||
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ exports.currentData = () ->
|
|||
if err or resp.statusCode isnt 200
|
||||
log JSON.stringify body
|
||||
else
|
||||
exports.pushEvent body
|
||||
pushEvent body
|
||||
|
||||
###
|
||||
Emits one event per day if the temperature today raises above user defined threshold
|
||||
|
|
@ -37,7 +37,7 @@ exports.temperatureOverThreshold = () ->
|
|||
else
|
||||
#If temperature is above threshold
|
||||
if body.main.temp_max - 272.15 > params.tempThreshold
|
||||
exports.pushEvent
|
||||
pushEvent
|
||||
threshold: params.tempThreshold
|
||||
measured: body.main.temp_max - 272.15
|
||||
|
||||
|
|
|
|||
|
|
@ -34,9 +34,8 @@ sandbox =
|
|||
log: console.log
|
||||
debug: console.log
|
||||
exports: {}
|
||||
|
||||
sandbox.exports.pushEvent = ( obj ) ->
|
||||
console.log obj
|
||||
pushEvent: ( obj ) ->
|
||||
console.log obj
|
||||
|
||||
vm.runInNewContext src, sandbox, sandbox.id
|
||||
|
||||
|
|
|
|||
|
|
@ -260,14 +260,14 @@ Components Manager
|
|||
};
|
||||
|
||||
forgeModule = (function(_this) {
|
||||
return function(user, oPayload, dbMod, callback) {
|
||||
return function(user, oPayload, modType, dbMod, callback) {
|
||||
var answ;
|
||||
answ = hasRequiredParams(['id', 'params', 'lang', 'data'], oPayload);
|
||||
if (answ.code !== 200) {
|
||||
return callback(answ);
|
||||
} else {
|
||||
if (oPayload.overwrite) {
|
||||
return storeModule(user, oPayload, dbMod, callback);
|
||||
return storeModule(user, oPayload, modType, dbMod, callback);
|
||||
} else {
|
||||
return dbMod.getModule(user.username, oPayload.id, function(err, mod) {
|
||||
if (mod) {
|
||||
|
|
@ -275,7 +275,7 @@ Components Manager
|
|||
answ.message = 'Module name already existing: ' + oPayload.id;
|
||||
return callback(answ);
|
||||
} else {
|
||||
return storeModule(user, oPayload, dbMod, callback);
|
||||
return storeModule(user, oPayload, modType, dbMod, callback);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
@ -284,10 +284,12 @@ Components Manager
|
|||
})(this);
|
||||
|
||||
storeModule = (function(_this) {
|
||||
return function(user, oPayload, dbMod, callback) {
|
||||
return function(user, oPayload, modType, dbMod, callback) {
|
||||
var src;
|
||||
src = oPayload.data;
|
||||
return dynmod.compileString(src, user.username, 'dummyRule', oPayload.id, oPayload.lang, null, function(cm) {
|
||||
return dynmod.compileString(src, user.username, {
|
||||
id: 'dummyRule'
|
||||
}, oPayload.id, oPayload.lang, modType, null, function(cm) {
|
||||
var answ, funcs, id, name, _ref;
|
||||
answ = cm.answ;
|
||||
if (answ.code === 200) {
|
||||
|
|
@ -407,7 +409,7 @@ Components Manager
|
|||
}
|
||||
},
|
||||
forge_event_poller: function(user, oPayload, callback) {
|
||||
return forgeModule(user, oPayload, db.eventPollers, callback);
|
||||
return forgeModule(user, oPayload, "eventpoller", db.eventPollers, callback);
|
||||
},
|
||||
delete_event_poller: function(user, oPayload, callback) {
|
||||
var answ;
|
||||
|
|
@ -463,7 +465,7 @@ Components Manager
|
|||
}
|
||||
},
|
||||
forge_action_invoker: function(user, oPayload, callback) {
|
||||
return forgeModule(user, oPayload, db.actionInvokers, callback);
|
||||
return forgeModule(user, oPayload, "actioninvoker", db.actionInvokers, callback);
|
||||
},
|
||||
delete_action_invoker: function(user, oPayload, callback) {
|
||||
var answ;
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ Dynamic Modules
|
|||
*/
|
||||
|
||||
(function() {
|
||||
var cryptoJS, cs, db, encryption, exports, fTryToLoadModule, getFunctionParamNames, importio, logFunction, needle, regexpComments, request, vm;
|
||||
var cryptoJS, cs, db, encryption, exports, fPushEvent, fTryToLoadModule, getFunctionParamNames, importio, logFunction, needle, regexpComments, request, vm;
|
||||
|
||||
db = require('./persistence');
|
||||
|
||||
|
|
@ -76,7 +76,7 @@ Dynamic Modules
|
|||
*/
|
||||
|
||||
exports.compileString = (function(_this) {
|
||||
return function(src, userId, ruleId, modId, lang, dbMod, cb) {
|
||||
return function(src, userId, oRule, modId, lang, modType, dbMod, cb) {
|
||||
var err;
|
||||
if (lang === 'CoffeeScript') {
|
||||
try {
|
||||
|
|
@ -104,22 +104,40 @@ Dynamic Modules
|
|||
oParam = _ref[name];
|
||||
oParams[name] = encryption.decrypt(oParam.value);
|
||||
}
|
||||
_this.log.info("DM | Loaded user defined params for " + userId + ", " + ruleId + ", " + modId);
|
||||
_this.log.info("DM | Loaded user defined params for " + userId + ", " + oRule.id + ", " + modId);
|
||||
} catch (_error) {
|
||||
err = _error;
|
||||
_this.log.warn("DM | Error during parsing of user defined params for " + userId + ", " + ruleId + ", " + modId);
|
||||
_this.log.warn("DM | Error during parsing of user defined params for " + userId + ", " + oRule.id + ", " + modId);
|
||||
_this.log.warn(err);
|
||||
}
|
||||
return fTryToLoadModule(userId, ruleId, modId, src, dbMod, oParams, cb);
|
||||
return fTryToLoadModule(userId, oRule, modId, src, modType, dbMod, oParams, cb);
|
||||
});
|
||||
} else {
|
||||
return fTryToLoadModule(userId, ruleId, modId, src, dbMod, null, cb);
|
||||
return fTryToLoadModule(userId, oRule, modId, src, modType, dbMod, null, cb);
|
||||
}
|
||||
};
|
||||
})(this);
|
||||
|
||||
fPushEvent = function(userId, oRule, modType) {
|
||||
return function(obj) {
|
||||
var rand, timestamp;
|
||||
timestamp = (new Date()).toISOString();
|
||||
rand = (Math.floor(Math.random() * 10e9)).toString(16).toUpperCase();
|
||||
if (modType === 'eventpoller') {
|
||||
return db.pushEvent({
|
||||
event: oRule.event + '_created:' + oRule.timestamp,
|
||||
eventid: "" + userId + "_" + oRule.event + "_UTC|" + timestamp + "_" + rand,
|
||||
payload: obj
|
||||
});
|
||||
} else {
|
||||
obj.eventid = "" + userId + "_" + oRule.event + "_UTC|" + timestamp + "_" + rand;
|
||||
return db.pushEvent(obj);
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
fTryToLoadModule = (function(_this) {
|
||||
return function(userId, ruleId, modId, src, dbMod, params, cb) {
|
||||
return function(userId, oRule, modId, src, modType, dbMod, params, cb) {
|
||||
var answ, err, fName, fRegisterArguments, func, logFunc, msg, oFuncArgs, oFuncParams, sandbox, _ref;
|
||||
if (!params) {
|
||||
params = {};
|
||||
|
|
@ -129,9 +147,9 @@ Dynamic Modules
|
|||
message: 'Successfully compiled'
|
||||
};
|
||||
_this.log.info("DM | Running module '" + modId + "' for user '" + userId + "'");
|
||||
logFunc = logFunction(userId, ruleId, modId);
|
||||
logFunc = logFunction(userId, oRule.id, modId);
|
||||
sandbox = {
|
||||
id: "" + userId + "." + ruleId + "." + modId + ".vm",
|
||||
id: "" + userId + "." + oRule.id + "." + modId + ".vm",
|
||||
params: params,
|
||||
needle: needle,
|
||||
importio: importio,
|
||||
|
|
@ -139,7 +157,8 @@ Dynamic Modules
|
|||
cryptoJS: cryptoJS,
|
||||
log: logFunc,
|
||||
debug: console.log,
|
||||
exports: {}
|
||||
exports: {},
|
||||
pushEvent: fPushEvent(userId, oRule, modType)
|
||||
};
|
||||
try {
|
||||
vm.runInNewContext(src, sandbox, sandbox.id);
|
||||
|
|
@ -152,7 +171,7 @@ Dynamic Modules
|
|||
}
|
||||
answ.message = 'Loading Module failed: ' + msg;
|
||||
}
|
||||
_this.log.info("DM | Module '" + modId + "' ran successfully for user '" + userId + "' in rule '" + ruleId + "'");
|
||||
_this.log.info("DM | Module '" + modId + "' ran successfully for user '" + userId + "' in rule '" + oRule.id + "'");
|
||||
oFuncParams = {};
|
||||
oFuncArgs = {};
|
||||
_ref = sandbox.exports;
|
||||
|
|
@ -167,17 +186,17 @@ Dynamic Modules
|
|||
if (obj) {
|
||||
try {
|
||||
oFuncArgs[fName] = JSON.parse(obj);
|
||||
return _this.log.info("DM | Found and attached user-specific arguments to " + userId + ", " + ruleId + ", " + modId + ": " + obj);
|
||||
return _this.log.info("DM | Found and attached user-specific arguments to " + userId + ", " + oRule.id + ", " + modId + ": " + obj);
|
||||
} catch (_error) {
|
||||
err = _error;
|
||||
_this.log.warn("DM | Error during parsing of user-specific arguments for " + userId + ", " + ruleId + ", " + modId);
|
||||
_this.log.warn("DM | Error during parsing of user-specific arguments for " + userId + ", " + oRule.id + ", " + modId);
|
||||
return _this.log.warn(err);
|
||||
}
|
||||
}
|
||||
};
|
||||
};
|
||||
for (func in oFuncParams) {
|
||||
dbMod.getUserArguments(userId, ruleId, modId, func, fRegisterArguments(func));
|
||||
dbMod.getUserArguments(userId, oRule.id, modId, func, fRegisterArguments(func));
|
||||
}
|
||||
}
|
||||
return cb({
|
||||
|
|
|
|||
18
js/engine.js
18
js/engine.js
|
|
@ -168,7 +168,7 @@ Engine
|
|||
if (!oMyRule.actions[moduleName] || oMyRule.rule.id === updatedRuleId) {
|
||||
return db.actionInvokers.getModule(userName, moduleName, function(err, obj) {
|
||||
if (obj) {
|
||||
return dynmod.compileString(obj.data, userName, oMyRule.rule.id, moduleName, obj.lang, db.actionInvokers, function(result) {
|
||||
return dynmod.compileString(obj.data, userName, oMyRule.rule, moduleName, obj.lang, "actioninvoker", db.actionInvokers, function(result) {
|
||||
if (result.answ.code === 200) {
|
||||
_this.log.info("EN | Module '" + moduleName + "' successfully loaded for userName '" + userName + "' in rule '" + oMyRule.rule.id + "'");
|
||||
} else {
|
||||
|
|
@ -312,13 +312,15 @@ Engine
|
|||
oArg = _ref[_i];
|
||||
arrSelectors = oArg.value.match(/#\{(.*?)\}/g);
|
||||
argument = oArg.value;
|
||||
for (_j = 0, _len1 = arrSelectors.length; _j < _len1; _j++) {
|
||||
sel = arrSelectors[_j];
|
||||
selector = sel.substring(2, sel.length - 1);
|
||||
data = jsonQuery(evt.payload, selector).nodes()[0];
|
||||
argument = argument.replace(sel, data);
|
||||
if (oArg.value === sel) {
|
||||
argument = data;
|
||||
if (arrSelectors) {
|
||||
for (_j = 0, _len1 = arrSelectors.length; _j < _len1; _j++) {
|
||||
sel = arrSelectors[_j];
|
||||
selector = sel.substring(2, sel.length - 1);
|
||||
data = jsonQuery(evt.payload, selector).nodes()[0];
|
||||
argument = argument.replace(sel, data);
|
||||
if (oArg.value === sel) {
|
||||
argument = data;
|
||||
}
|
||||
}
|
||||
}
|
||||
arrArgs.push(argument);
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ Dynamic Modules
|
|||
*/
|
||||
|
||||
(function() {
|
||||
var db, dynmod, encryption, fCallFunction, fCheckAndRun, fLoadModule, fPushEvent, isRunning, listUserModules, log, logconf, logger, pollLoop;
|
||||
var db, dynmod, encryption, fCallFunction, fCheckAndRun, fLoadModule, isRunning, listUserModules, log, logconf, logger, pollLoop;
|
||||
|
||||
logger = require('./logging');
|
||||
|
||||
|
|
@ -85,7 +85,7 @@ Dynamic Modules
|
|||
if (!obj) {
|
||||
return log.warn("EP | Strange... no module retrieved: " + arrName[0]);
|
||||
} else {
|
||||
return dynmod.compileString(obj.data, msg.user, msg.rule.id, arrName[0], obj.lang, db.eventPollers, function(result) {
|
||||
return dynmod.compileString(obj.data, msg.user, msg.rule, arrName[0], obj.lang, "eventpoller", db.eventPollers, function(result) {
|
||||
var nd, now, oUser, start;
|
||||
if (!result.answ === 200) {
|
||||
log.error("EP | Compilation of code failed! " + msg.user + ", " + msg.rule.id + ", " + arrName[0]);
|
||||
|
|
@ -103,7 +103,6 @@ Dynamic Modules
|
|||
module: result.module,
|
||||
logger: result.logger
|
||||
};
|
||||
oUser[msg.rule.id].module.pushEvent = fPushEvent(msg.user, msg.rule.id, oUser[msg.rule.id]);
|
||||
start = new Date(msg.rule.event_start);
|
||||
nd = new Date();
|
||||
now = new Date();
|
||||
|
|
@ -129,16 +128,6 @@ Dynamic Modules
|
|||
}
|
||||
};
|
||||
|
||||
fPushEvent = function(userId, ruleId, oRule) {
|
||||
return function(obj) {
|
||||
return db.pushEvent({
|
||||
event: oRule.id + '_created:' + oRule.timestamp,
|
||||
eventid: "polled " + oRule.id + " " + userId + "_UTC|" + ((new Date()).toISOString()),
|
||||
payload: obj
|
||||
});
|
||||
};
|
||||
};
|
||||
|
||||
fCheckAndRun = function(userId, ruleId, timestamp) {
|
||||
return function() {
|
||||
var oRule;
|
||||
|
|
|
|||
|
|
@ -51,14 +51,14 @@ exports.testCompile = ( test ) ->
|
|||
|
||||
paramOne = 'First Test'
|
||||
code = "exports.testFunc = () ->\n\t'#{ paramOne }'"
|
||||
dm.compileString code, 'userOne', 'ruleOne', 'moduleOne', 'CoffeeScript', null, ( result ) ->
|
||||
dm.compileString code, 'userOne', 'ruleOne', 'moduleOne', 'CoffeeScript', 'eventpoller', null, ( result ) ->
|
||||
test.strictEqual 200, result.answ.code
|
||||
moduleOne = result.module
|
||||
test.strictEqual paramOne, moduleOne.testFunc(), "Other result expected"
|
||||
|
||||
paramTwo = 'Second Test'
|
||||
code = "exports.testFunc = () ->\n\t'#{ paramTwo }'"
|
||||
dm.compileString code, 'userOne', 'ruleOne', 'moduleOne', 'CoffeeScript', null, ( result ) ->
|
||||
dm.compileString code, 'userOne', 'ruleOne', 'moduleOne', 'CoffeeScript', 'eventpoller', null, ( result ) ->
|
||||
test.strictEqual 200, result.answ.code
|
||||
moduleTwo = result.module
|
||||
test.strictEqual paramTwo, moduleTwo.testFunc(), "Other result expected"
|
||||
|
|
|
|||
Loading…
Reference in a new issue