hubot-sample
Version:
teste de adapter
191 lines (148 loc) • 5.84 kB
text/coffeescript
require 'coffeescript/register'
natural = require 'natural'
classifier = {}
lang = (process.env.HUBOT_LANG || 'en')
PorterStemmer = natural.PorterStemmer
if lang != 'en'
lang_captilize = lang.charAt(0).toUpperCase() + lang.slice(1)
PorterStemmer = natural['PorterStemmer' + lang_captilize]
actionHandler = require './action-handler'
# Classifier that holds all root level interactions
root_classifier = {}
error_count = 0
ROOT_LEVEL_NAME = "root"
classifyInteraction = (interaction, classifier) ->
if not interaction.expect?
console.warn("\t!! Interaction with no expects: " + interaction.name)
return
console.log('\tProcessing interaction: ' + interaction.name)
if not Array.isArray interaction.expect
interaction.expect = [interaction.expect]
for doc in interaction.expect
if typeof(doc) != 'string'
doc = '' + doc
classifier.addDocument(doc, interaction.name)
if interaction.next?.interactions? and not interaction.next?.classifier?
if not Array.isArray interaction.next.interactions
interactions.next.interactions = [interactions.next.interactions]
interaction.next.classifier = new natural.LogisticRegressionClassifier(
PorterStemmer
)
for nextInteractionName in interaction.next.interactions
nextInteraction = global.config.interactions.find (n) ->
return n.name is nextInteractionName
if not nextInteraction?
console.log 'No valid interaction for', nextInteractionName
continue
classifyInteraction nextInteraction, interaction.next.classifier
interaction.next.classifier.train()
classifier.train = () ->
console.log 'Processing interactions'
console.time 'Processing interactions (Done)'
root_classifier = new natural.LogisticRegressionClassifier(PorterStemmer)
for interaction in global.config.interactions
if (not interaction.level? or
(Array.isArray(interaction.level) and
interaction.level.includes(ROOT_LEVEL_NAME)) or
interaction.level == ROOT_LEVEL_NAME)
classifyInteraction interaction, root_classifier
console.log 'Training Bot (This could be take a while...)'
root_classifier.train()
console.timeEnd 'Processing interactions (Done)'
setContext = (res, context) ->
key = 'context_' + res.envelope.room + '_' + res.envelope.user.id
console.log 'set context', context
res.robot.brain.set(key, context)
getContext = (res) ->
key = 'context_' + res.envelope.room + '_' + res.envelope.user.id
return res.robot.brain.get(key)
isDebugMode = (res) ->
key = 'configure_debug-mode_' + res.envelope.room
return (res.robot.brain.get(key) == 'true')
getDebugCount = (res) ->
key = 'configure_debug-count_' + res.envelope.room
if res.robot.brain.get(key)
return res.robot.brain.get(key) - 1
else
return false
buildClassificationDebugMsg = (res, classifications) ->
list = ''
debugCount = getDebugCount(res)
if debugCount
classifications = classifications[0..debugCount]
for classification, i in classifications
list = (list.concat 'Label: ' + classification.label + ' Score: ' +
classification.value + '\n')
newMsg = {
channel: res.envelope.user.roomID,
msg: "Classifications considered:",
attachments: [{
text: list
}]
}
return newMsg
incErrors = (res) ->
key = 'errors_' + res.envelope.room + '_' + res.envelope.user.id
errors = res.robot.brain.get(key) or 0
errors++
console.log 'inc errors ', errors
res.robot.brain.set(key, errors)
return errors
clearErrors = (res) ->
console.log 'clear errors'
key = 'errors_' + res.envelope.room + '_' + res.envelope.user.id
res.robot.brain.set(key, 0)
classifier.processMessage = (res, msg) ->
context = getContext(res)
currentClassifier = root_classifier
trust = global.config.trust
interaction = undefined
debugMode = isDebugMode(res)
console.log 'context ->', context
if context
interaction = global.config.interactions.find (interaction) ->
interaction.name is context
if interaction? and interaction.next?.classifier?
currentClassifier = interaction.next.classifier
if interaction.next.trust?
trust = interaction.next.trust
classifications = currentClassifier.getClassifications(msg)
console.log 'classifications ->', classifications[0..4]
if debugMode
newMsg = buildClassificationDebugMsg(res, classifications)
robot.adapter.chatdriver.customMessage(newMsg)
if classifications[0].value >= trust
clearErrors res
[node_name, sub_node_name] = classifications[0].label.split('|')
console.log({ node_name, sub_node_name })
int = global.config.interactions.find (interaction) ->
interaction.name is node_name
if int.classifier?
int.classifier.getClassifications(msg)
else
if Array.isArray interaction?.next?.error
error_count = incErrors res
error_node_name = interaction.next.error[error_count - 1]
if not error_node_name?
clearErrors res
error_node_name = interaction.next.error[0]
else if interaction?.next?
setContext(res, undefined)
return classifier.processMessage(res, msg)
else
error_count = incErrors res
if error_count > actionHandler.errorNodesCount()
clearErrors res
error_count = incErrors res
error_node_name = "error-" + error_count
currentInteraction = global.config.interactions.find (interaction) ->
interaction.name is node_name or interaction.name is error_node_name
if not currentInteraction?
clearErrors res
return console.log 'Invalid interaction [' + node_name + ']'
if currentInteraction.context == 'clear'
setContext(res, undefined)
else if node_name?
setContext(res, node_name)
return node_name or error_node_name
module.exports = classifier