Skip to content

Commit

Permalink
Refactory dialog to Watson alternative component
Browse files Browse the repository at this point in the history
  • Loading branch information
ralphg6 committed Feb 7, 2020
1 parent d20cbe9 commit d9e2b2a
Show file tree
Hide file tree
Showing 10 changed files with 111 additions and 122 deletions.
10 changes: 0 additions & 10 deletions david/__main__.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
import david.config
from david.adapters.adapter import MessageAdapter
from david.assistant import Assistant
from david.dialog import fetch_dialog
from david.googleadap import GoogleWebHook
from david.registry import Registry

Expand Down Expand Up @@ -60,15 +59,6 @@ def google():
return jsonify(googleWH.handle(data))


# @app.route('/data/dialog')
# def data_dialog():
# return jsonify(fetch_dialog())

# @app.route('/data/know')
# def data_know():
# return jsonify(fetch_know())


def main() -> None:
app.run(host="0.0.0.0")

Expand Down
48 changes: 19 additions & 29 deletions david/assistant.py
Original file line number Diff line number Diff line change
@@ -1,43 +1,33 @@
from david.brain import Brain
from david.components.dialogue import WatsonAlternative
from david.components.nlu import SimpleNLU
from david.config import DavidConfig
from david.constants import (
CONTEXT_ATTRIBUTE,
ENTITIES_ATTRIBUTE,
INTENTS_ATTRIBUTE,
TEXT_ATTRIBUTE,
)
from david.dialog import Dialog
from david.constants import DEFAULT_DATA_PATH, DEFAULT_MODELS_PATH, TEXT_ATTRIBUTE
from david.training_data.formats import JsonReader
from david.typing import Message

MODEL_FILE = "intent_model.json"
DIALOG_FILE = "dialog.json"


class Assistant:
def __init__(self, config: DavidConfig):
self.brain = Brain(config)
self.dialog = Dialog()
self.config = config
self.dialog = WatsonAlternative.load(
{"file": DIALOG_FILE}, model_dir=DEFAULT_DATA_PATH
)
self.nlu = SimpleNLU.create({}, self.config)
self.train()

def train(self):
self.brain.train()
self.dialog.train()
training_data = JsonReader.load(self.config)
self.nlu.train(training_data, self.config)
self.nlu.persist(file_name=MODEL_FILE, model_dir=DEFAULT_MODELS_PATH)

def respond(self, message, context={}):
text = message.get(TEXT_ATTRIBUTE)
message = Message.build(text)

message = self.brain.process(text)

intents = message.get(INTENTS_ATTRIBUTE)
entities = message.get(ENTITIES_ATTRIBUTE)
context = message.get(CONTEXT_ATTRIBUTE)

# print("intents", intents)
dialog_node = self.dialog.dialog(input, context, intents, entities)

message.output = dialog_node["output"]

# return {
# "context": context,
# "intents": intents,
# "entities": entities,
# "output": dialog_node["output"],
# }
self.nlu.process(message)
self.dialog.process(message)

return message
35 changes: 0 additions & 35 deletions david/brain.py

This file was deleted.

1 change: 1 addition & 0 deletions david/components/dialogue/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from david.components.dialogue.watsonalternative import WatsonAlternative
87 changes: 87 additions & 0 deletions david/components/dialogue/watsonalternative.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
import json
import os
from typing import Any, Dict, Optional, Text

from david.components.component import Component
from david.constants import (
CONTEXT_ATTRIBUTE,
ENTITIES_ATTRIBUTE,
INTENTS_ATTRIBUTE,
TEXT_ATTRIBUTE,
)
from david.typing import Message
from david.typing.model import Metadata


def get_dialog_welcome(dialog_nodes):
return dialog_nodes[0]


def get_dialog_anythinelse(dialog_nodes):
return dialog_nodes[len(dialog_nodes) - 1]


def evalCondition(condition, context, intent, entities):
return condition == "#" + intent


class WatsonAlternative(Component):
def __init__(
self,
component_config: Optional[Dict[Text, Any]] = None,
dialog_nodes: Dict = None,
) -> None:
super().__init__(component_config)

self.dialog_nodes = dialog_nodes

@classmethod
def load(
cls,
meta: Dict[Text, Any],
model_dir: Optional[Text] = None,
model_metadata: Optional["Metadata"] = None,
cached_component: Optional["Component"] = None,
**kwargs: Any,
) -> "Component":
"""Load this component from file.
After a component has been trained, it will be persisted by
calling `persist`. When the pipeline gets loaded again,
this component needs to be able to restore itself.
Components can rely on any context attributes that are
created by :meth:`components.Component.create`
calls to components previous
to this one."""

file_name = meta.get("file")
model_file = os.path.join(model_dir, file_name)

if os.path.exists(model_file):
with open(model_file) as f:
dialog_nodes = json.load(f)
return cls(meta, dialog_nodes)
else:
return cls(meta)

def process(self, message: Message, **kwargs: Any) -> None:

text = message.get(TEXT_ATTRIBUTE)
intents = message.get(INTENTS_ATTRIBUTE)
entities = message.get(ENTITIES_ATTRIBUTE)
context = message.get(CONTEXT_ATTRIBUTE)

dialog_node = self.__dialog(text, context, intents, entities)

message.output = dialog_node["output"]

def __dialog(self, input, context, intents, entities):
if input == "":
return get_dialog_welcome(self.dialog_nodes)

if len(intents) > 0:
intent = intents[0]["intent"]
for dialog_node in self.dialog_nodes:
if evalCondition(dialog_node["condition"], context, intent, entities):
return dialog_node

return get_dialog_anythinelse(self.dialog_nodes)
1 change: 1 addition & 0 deletions david/components/nlu/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from david.components.nlu.simplenlu import SimpleNLU
3 changes: 0 additions & 3 deletions david/components/nlu/simplenlu.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,6 @@ def simmilarity(a, b):


class SimpleNLU(Component):
def __init__(self):
print("SimpleNLU")

def __init__(
self,
component_config: Optional[Dict[Text, Any]] = None,
Expand Down
2 changes: 2 additions & 0 deletions david/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@

DEFAULT_DATA_PATH = "data"

DEFAULT_MODELS_PATH = "models"

DEFAULT_CONFIG_PATH = "config.yml"

TRAIN_DATA_FILE = "know.json"
Expand Down
45 changes: 0 additions & 45 deletions david/dialog.py

This file was deleted.

1 change: 1 addition & 0 deletions david/training_data/formats/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from david.training_data.formats.json import JsonReader

0 comments on commit d9e2b2a

Please sign in to comment.