diff --git a/.idea/gstfaqbot.iml b/.idea/gstfaqbot.iml new file mode 100644 index 0000000..6f63a63 --- /dev/null +++ b/.idea/gstfaqbot.iml @@ -0,0 +1,12 @@ + + + + + + + + + + \ No newline at end of file diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..b411b34 --- /dev/null +++ b/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,31 @@ + + + + \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..5d75fec --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,7 @@ + + + + ApexVCS + + + \ No newline at end of file diff --git a/.idea/modules.xml b/.idea/modules.xml new file mode 100644 index 0000000..0fb6093 --- /dev/null +++ b/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..94a25f7 --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/.idea/workspace.xml b/.idea/workspace.xml new file mode 100644 index 0000000..925d96a --- /dev/null +++ b/.idea/workspace.xml @@ -0,0 +1,648 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + exe + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 1504948956941 + + + 1505098995033 + + + 1505099371820 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + file://$PROJECT_DIR$/app.py + 24 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/AV_GST FAQ Bot with Rasa.docx b/AV_GST FAQ Bot with Rasa.docx new file mode 100644 index 0000000..020850f Binary files /dev/null and b/AV_GST FAQ Bot with Rasa.docx differ diff --git a/README.md b/README.md new file mode 100644 index 0000000..4774eaf --- /dev/null +++ b/README.md @@ -0,0 +1,34 @@ +# GST FAQ Bot with Rasa-NLU +Set of scripts to build a chatbot which will answer FAQ about Goods and Services Tax (GST) India. +Copyright (C) 2017 Yogesh H Kulkarni + +## License: +This program is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation; either version 2 +of the License, or any later version. + +## Scripts: +* app.py: Chatbot UI built using Flask, using templates/*.html +* engine.py: Chatbot core logic as well as knowledgebase. +* config.json: Rasa NLU settings for training as well as executing intent extraction +* run_training: Windows batch file to build trained modeling +* run_server: Windows batch file to execute Rasa-NLU server. + +## Dependencies: +* Needs Python 3.5 + +## ToDos +* Add more training data +* Entity extraction not working as desired, find out more. +* Etc. + +## References +* Rasa-NLU [installation](https://github.com/RasaHQ/rasa_nlu) +* Bhavani Ravi’s event-bot [code](https://github.com/bhavaniravi/rasa-site-bot), Youtube [Video](https://www.youtube.com/watch?v=ojuq0vBIA-g) +* GST FAQs: + * Government [Documentation](http://www.cbec.gov.in/resources//htdocs-cbec/deptt_offcr/faq-on-gst.pdf) + * GST India [Documentation](http://www.gstindia.com/frequently-asked-questions-faqs-on-goods-and-services-tax-gst/) + +## Disclaimer: +* Author (yogeshkulkarni@yahoo.com) gives no guarantee of the results of the program. It is just a fun script. Lot of improvements are still to be made. So, don’t depend on it at all. diff --git a/__pycache__/engine.cpython-35.pyc b/__pycache__/engine.cpython-35.pyc new file mode 100644 index 0000000..c37c4f3 Binary files /dev/null and b/__pycache__/engine.cpython-35.pyc differ diff --git a/app.py b/app.py new file mode 100644 index 0000000..14139c2 --- /dev/null +++ b/app.py @@ -0,0 +1,44 @@ +# Ref: https://github.com/bhavaniravi/rasa-site-bot +from flask import Flask +from flask import render_template,jsonify,request +import requests +# from models import * +from engine import * +import random + + +app = Flask(__name__) +app.secret_key = '12345' + +@app.route('/') +def hello_world(): + return render_template('home.html') + +get_random_response = lambda intent:random.choice(intent_response_dict[intent]) + + +@app.route('/chat',methods=["POST"]) +def chat(): + try: + user_message = request.form["text"] + response = requests.get("http://localhost:5000/parse",params={"q":user_message}) + response = response.json() + entities = response.get("entities") + topresponse = response["topScoringIntent"] + intent = topresponse.get("intent") + print("Intent {}, Entities {}".format(intent,entities)) + if intent == "gst-info": + response_text = gst_info(entities)# "Sorry will get answer soon" #get_event(entities["day"],entities["time"],entities["place"]) + elif intent == "gst-query": + response_text = gst_query(entities) + else: + response_text = get_random_response(intent) + return jsonify({"status":"success","response":response_text}) + except Exception as e: + print(e) + return jsonify({"status":"success","response":"Sorry I am not trained to do that yet..."}) + + +app.config["DEBUG"] = True +if __name__ == "__main__": + app.run(port=8080) diff --git a/config.json b/config.json new file mode 100644 index 0000000..3178d27 --- /dev/null +++ b/config.json @@ -0,0 +1,6 @@ +{ + "pipeline": "spacy_sklearn", + "path" : "models/", + "data" : "data/gstfaq-data.json", + "num_threads":10 +} \ No newline at end of file diff --git a/data/demo-rasa.json b/data/demo-rasa.json new file mode 100644 index 0000000..7b3cec9 --- /dev/null +++ b/data/demo-rasa.json @@ -0,0 +1,287 @@ +{ + "rasa_nlu_data": { + "entity_examples": [ + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "howdy", + "intent": "greet", + "entities": [] + }, + { + "text": "hey there", + "intent": "greet", + "entities": [] + }, + { + "text": "hello", + "intent": "greet", + "entities": [] + }, + { + "text": "hi", + "intent": "greet", + "entities": [] + }, + { + "text": "i'm looking for a place to eat", + "intent": "restaurant_search", + "entities": [] + }, + { + "text": "i'm looking for a place in the north of town", + "intent": "restaurant_search", + "entities": [ + { + "start": 31, + "end": 36, + "value": "north", + "entity": "location" + } + ] + }, + { + "text": "show me chinese restaurants", + "intent": "restaurant_search", + "entities": [ + { + "start": 8, + "end": 15, + "value": "chinese", + "entity": "cuisine" + } + ] + }, + { + "text": "yes", + "intent": "affirm", + "entities": [] + }, + { + "text": "yep", + "intent": "affirm", + "entities": [] + }, + { + "text": "yeah", + "intent": "affirm", + "entities": [] + }, + { + "text": "show me a mexican place in the centre", + "intent": "restaurant_search", + "entities": [ + { + "start": 31, + "end": 37, + "value": "centre", + "entity": "location" + }, + { + "start": 10, + "end": 17, + "value": "mexican", + "entity": "cuisine" + } + ] + }, + { + "text": "bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "goodbye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "good bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "stop", + "intent": "goodbye", + "entities": [] + }, + { + "text": "end", + "intent": "goodbye", + "entities": [] + }, + { + "text": "i am looking for an indian spot", + "intent": "restaurant_search", + "entities": [ + { + "start": 20, + "end": 26, + "value": "indian", + "entity": "cuisine" + } + ] + }, + { + "text": "search for restaurants", + "intent": "restaurant_search", + "entities": [] + }, + { + "text": "anywhere in the west", + "intent": "restaurant_search", + "entities": [ + { + "start": 16, + "end": 20, + "value": "west", + "entity": "location" + } + ] + }, + { + "text": "central indian restaurant", + "intent": "restaurant_search", + "entities": [ + { + "start": 0, + "end": 7, + "value": "central", + "entity": "location" + }, + { + "start": 8, + "end": 14, + "value": "indian", + "entity": "cuisine" + } + ] + }, + { + "text": "indeed", + "intent": "affirm", + "entities": [] + }, + { + "text": "that's right", + "intent": "affirm", + "entities": [] + }, + { + "text": "ok", + "intent": "affirm", + "entities": [] + }, + { + "text": "great", + "intent": "affirm", + "entities": [] + } + ], + "intent_examples": [ + { + "text": "hey", + "intent": "greet" + }, + { + "text": "howdy", + "intent": "greet" + }, + { + "text": "hey there", + "intent": "greet" + }, + { + "text": "hello", + "intent": "greet" + }, + { + "text": "hi", + "intent": "greet" + }, + { + "text": "i'm looking for a place to eat", + "intent": "restaurant_search" + }, + { + "text": "i'm looking for a place in the north of town", + "intent": "restaurant_search" + }, + { + "text": "show me chinese restaurants", + "intent": "restaurant_search" + }, + { + "text": "yes", + "intent": "affirm" + }, + { + "text": "yep", + "intent": "affirm" + }, + { + "text": "yeah", + "intent": "affirm" + }, + { + "text": "show me a mexican place in the centre", + "intent": "restaurant_search" + }, + { + "text": "bye", + "intent": "goodbye" + }, + { + "text": "goodbye", + "intent": "goodbye" + }, + { + "text": "good bye", + "intent": "goodbye" + }, + { + "text": "stop", + "intent": "goodbye" + }, + { + "text": "end", + "intent": "goodbye" + }, + { + "text": "i am looking for an indian spot", + "intent": "restaurant_search" + }, + { + "text": "search for restaurants", + "intent": "restaurant_search" + }, + { + "text": "anywhere in the west", + "intent": "restaurant_search" + }, + { + "text": "central indian restaurant", + "intent": "restaurant_search" + }, + { + "text": "indeed", + "intent": "affirm" + }, + { + "text": "that's right", + "intent": "affirm" + }, + { + "text": "ok", + "intent": "affirm" + }, + { + "text": "great", + "intent": "affirm" + } + ] + } +} \ No newline at end of file diff --git a/data/gstfaq-data.json b/data/gstfaq-data.json new file mode 100644 index 0000000..af7d96d --- /dev/null +++ b/data/gstfaq-data.json @@ -0,0 +1,261 @@ +{ + "rasa_nlu_data": { + "common_examples": [ + { + "text": "who are you?", + "intent": "intro", + "entities": [] + }, + { + "text": "what do you do?", + "intent": "intro", + "entities": [] + }, + { + "text": "what can you do for me?", + "intent": "intro", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "howdy", + "intent": "greet", + "entities": [] + }, + { + "text": "hey there", + "intent": "greet", + "entities": [] + }, + { + "text": "hello", + "intent": "greet", + "entities": [] + }, + { + "text": "hi", + "intent": "greet", + "entities": [] + }, + { + "text": "yes", + "intent": "affirm", + "entities": [] + }, + { + "text": "yep", + "intent": "affirm", + "entities": [] + }, + { + "text": "yeah", + "intent": "affirm", + "entities": [] + }, + { + "text": "bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "goodbye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "good bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "stop", + "intent": "goodbye", + "entities": [] + }, + { + "text": "end", + "intent": "goodbye", + "entities": [] + }, + { + "text": "indeed", + "intent": "affirm", + "entities": [] + }, + { + "text": "that's right", + "intent": "affirm", + "entities": [] + }, + { + "text": "ok", + "intent": "affirm", + "entities": [] + }, + { + "text": "great", + "intent": "affirm", + "entities": [] + }, + { + "text": "What is GST", + "intent": "gst-info", + "entities": [ + { + "start": 8, + "end": 11, + "value": "GST", + "entity": "gst-info-value" + } + ] + }, + { + "text": "What are the benefits of GST", + "intent": "gst-info", + "entities": [ + { + "start": 13, + "end": 22, + "value": "benefits", + "entity": "gst-info-value" + } + ] + }, + { + "text": "What are the benefits of GST for business", + "intent": "gst-info", + "entities": [ + { + "start": 13, + "end": 22, + "value": "benefits", + "entity": "gst-explain-type" + }, + { + "start": 33, + "end": 41, + "value": "business", + "entity": "gst-explain-value" + } + ] + }, + { + "text": "What are the benefits of GST for government", + "intent": "gst-info", + "entities": [ + { + "start": 13, + "end": 22, + "value": "benefits", + "entity": "gst-info-type" + }, + { + "start": 33, + "end": 43, + "value": "government", + "entity": "gst-info-value" + } + ] + }, + { + "text": "What is GST rate for grains", + "intent": "gst-query", + "entities": [ + { + "start": 21, + "end": 27, + "value": "grains", + "entity": "gst-query-value" + }, + { + "start": 12, + "end": 17, + "value": "rate", + "entity": "gst-query-type" + } + ] + }, + { + "text": "What are goods exempt from GST", + "intent": "gst-query", + "entities": [ + { + "start": 15, + "end": 22, + "value": "exempt", + "entity": "gst-query-value" + }, + { + "start": 9, + "end": 15, + "value": "goods", + "entity": "gst-query-type" + } + ] + }, + { + "text": "What are services exempt from GST", + "intent": "gst-query", + "entities": [ + { + "start": 9, + "end": 18, + "value": "services", + "entity": "gst-query-value" + }, + { + "start": 18, + "end": 25, + "value": "exempt", + "entity": "gst-query-type" + } + ] + }, + { + "text": "What are Goods attracting 5% GST", + "intent": "gst-query", + "entities": [ + { + "start": 9, + "end": 15, + "value": "Goods", + "entity": "gst-query-type" + }, + { + "start": 26, + "end": 28, + "value": "5%", + "entity": "gst-query-value" + } + ] + }, + { + "text": "What are Goods attracting 12% GST", + "intent": "gst-query", + "entities": [ + { + "start": 9, + "end": 15, + "value": "Goods", + "entity": "gst-query-type" + }, + { + "start": 26, + "end": 29, + "value": "12%", + "entity": "gst-query-value" + } + ] + } + ] + } +} \ No newline at end of file diff --git a/data/gstfaq-data_orig.json b/data/gstfaq-data_orig.json new file mode 100644 index 0000000..58dbfc4 --- /dev/null +++ b/data/gstfaq-data_orig.json @@ -0,0 +1,381 @@ +{ + "rasa_nlu_data": { + "common_examples": [ + { + "text": "who are you?", + "intent": "intro", + "entities": [] + }, + { + "text": "what do you do?", + "intent": "intro", + "entities": [] + }, + { + "text": "what can you do for me?", + "intent": "intro", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "howdy", + "intent": "greet", + "entities": [] + }, + { + "text": "hey there", + "intent": "greet", + "entities": [] + }, + { + "text": "hello", + "intent": "greet", + "entities": [] + }, + { + "text": "hi", + "intent": "greet", + "entities": [] + }, + { + "text": "yes", + "intent": "affirm", + "entities": [] + }, + { + "text": "yep", + "intent": "affirm", + "entities": [] + }, + { + "text": "yeah", + "intent": "affirm", + "entities": [] + }, + { + "text": "bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "goodbye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "good bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "stop", + "intent": "goodbye", + "entities": [] + }, + { + "text": "end", + "intent": "goodbye", + "entities": [] + }, + { + "text": "indeed", + "intent": "affirm", + "entities": [] + }, + { + "text": "that's right", + "intent": "affirm", + "entities": [] + }, + { + "text": "ok", + "intent": "affirm", + "entities": [] + }, + { + "text": "great", + "intent": "affirm", + "entities": [] + }, + { + "text": "What is the event happening now", + "intent": "event-request", + "entities": [ + { + "start": 28, + "end": 31, + "value": "now", + "entity": "time" + } + ] + }, + { + "text": "What event is happening at Lecture hall 10 AM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 45, + "value": "10 AM", + "entity": "time" + }, + { + "start": 46, + "end": 51, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What is the event same time tomorrow", + "intent": "event-request", + "entities": [ + { + "start": 18, + "end": 27, + "value": "same time", + "entity": "time" + }, + { + "start": 28, + "end": 36, + "value": "tomorrow", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at Lecture hall 2 tommorrow 10 PM", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 41, + "value": "Lecture hall 2", + "entity": "place" + }, + { + "start": 52, + "end": 57, + "value": "tomorrow 10 PM", + "entity": "time" + }, + { + "start": 42, + "end": 51, + "value": "tomorrow", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6 AM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 44, + "value": "10 AM", + "entity": "time" + }, + { + "start": 45, + "end": 52, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6:30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 47, + "value": "10 AM", + "entity": "time" + }, + { + "start": 48, + "end": 55, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6 30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 47, + "value": "10 AM", + "entity": "time" + }, + { + "start": 48, + "end": 55, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at 6 30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 34, + "value": "6 30 PM", + "entity": "time" + }, + { + "start": 35, + "end": 40, + "value": "today", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at 6", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 28, + "value": "6", + "entity": "time" + } + ] + }, + { + "text": "What event is at 12", + "intent": "event-request", + "entities": [ + { + "start": 17, + "end": 19, + "value": "12", + "entity": "time" + } + ] + }, + { + "text": "list events before 12", + "intent": "event-request", + "entities": [ + { + "start": 19, + "end": 21, + "value": "12", + "entity": "time" + }, + { + "start": 12, + "end": 18, + "value": "before", + "entity": "relative-time" + } + ] + }, + { + "text": "list events after 5", + "intent": "event-request", + "entities": [ + { + "start": 18, + "end": 19, + "value": "5", + "entity": "time" + }, + { + "start": 12, + "end": 17, + "value": "before", + "entity": "relative-time" + } + ] + }, + { + "text": "when is the chatbot event happening", + "intent": "event-time", + "entities": [ + { + "start": 12, + "end": 19, + "value": "chatbot", + "entity": "event_name" + } + ] + }, + { + "text": "when is python 101 event happening", + "intent": "event-time", + "entities": [ + { + "start": 8, + "end": 18, + "value": "python 101", + "entity": "event_name" + } + ] + }, + { + "text": "what event is happening 2 tomorrow", + "intent": "event-request", + "entities": [ + { + "start": 24, + "end": 25, + "value": "2", + "entity": "time" + }, + { + "start": 26, + "end": 34, + "value": "2", + "entity": "time" + } + ] + } + ] + } +} diff --git a/data/sitebot-data.json b/data/sitebot-data.json new file mode 100644 index 0000000..58dbfc4 --- /dev/null +++ b/data/sitebot-data.json @@ -0,0 +1,381 @@ +{ + "rasa_nlu_data": { + "common_examples": [ + { + "text": "who are you?", + "intent": "intro", + "entities": [] + }, + { + "text": "what do you do?", + "intent": "intro", + "entities": [] + }, + { + "text": "what can you do for me?", + "intent": "intro", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "hey", + "intent": "greet", + "entities": [] + }, + { + "text": "howdy", + "intent": "greet", + "entities": [] + }, + { + "text": "hey there", + "intent": "greet", + "entities": [] + }, + { + "text": "hello", + "intent": "greet", + "entities": [] + }, + { + "text": "hi", + "intent": "greet", + "entities": [] + }, + { + "text": "yes", + "intent": "affirm", + "entities": [] + }, + { + "text": "yep", + "intent": "affirm", + "entities": [] + }, + { + "text": "yeah", + "intent": "affirm", + "entities": [] + }, + { + "text": "bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "goodbye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "good bye", + "intent": "goodbye", + "entities": [] + }, + { + "text": "stop", + "intent": "goodbye", + "entities": [] + }, + { + "text": "end", + "intent": "goodbye", + "entities": [] + }, + { + "text": "indeed", + "intent": "affirm", + "entities": [] + }, + { + "text": "that's right", + "intent": "affirm", + "entities": [] + }, + { + "text": "ok", + "intent": "affirm", + "entities": [] + }, + { + "text": "great", + "intent": "affirm", + "entities": [] + }, + { + "text": "What is the event happening now", + "intent": "event-request", + "entities": [ + { + "start": 28, + "end": 31, + "value": "now", + "entity": "time" + } + ] + }, + { + "text": "What event is happening at Lecture hall 10 AM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 45, + "value": "10 AM", + "entity": "time" + }, + { + "start": 46, + "end": 51, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What is the event same time tomorrow", + "intent": "event-request", + "entities": [ + { + "start": 18, + "end": 27, + "value": "same time", + "entity": "time" + }, + { + "start": 28, + "end": 36, + "value": "tomorrow", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at Lecture hall 2 tommorrow 10 PM", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 41, + "value": "Lecture hall 2", + "entity": "place" + }, + { + "start": 52, + "end": 57, + "value": "tomorrow 10 PM", + "entity": "time" + }, + { + "start": 42, + "end": 51, + "value": "tomorrow", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6 AM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 44, + "value": "10 AM", + "entity": "time" + }, + { + "start": 45, + "end": 52, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6:30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 47, + "value": "10 AM", + "entity": "time" + }, + { + "start": 48, + "end": 55, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at Lecture hall 6 30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 40, + "end": 47, + "value": "10 AM", + "entity": "time" + }, + { + "start": 48, + "end": 55, + "value": "today", + "entity": "day" + }, + { + "start": 27, + "end": 39, + "value": "Lecture hall", + "entity": "place" + } + ] + }, + { + "text": "What event is happening at 6 30 PM today", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 34, + "value": "6 30 PM", + "entity": "time" + }, + { + "start": 35, + "end": 40, + "value": "today", + "entity": "day" + } + ] + }, + { + "text": "What event is happening at 6", + "intent": "event-request", + "entities": [ + { + "start": 27, + "end": 28, + "value": "6", + "entity": "time" + } + ] + }, + { + "text": "What event is at 12", + "intent": "event-request", + "entities": [ + { + "start": 17, + "end": 19, + "value": "12", + "entity": "time" + } + ] + }, + { + "text": "list events before 12", + "intent": "event-request", + "entities": [ + { + "start": 19, + "end": 21, + "value": "12", + "entity": "time" + }, + { + "start": 12, + "end": 18, + "value": "before", + "entity": "relative-time" + } + ] + }, + { + "text": "list events after 5", + "intent": "event-request", + "entities": [ + { + "start": 18, + "end": 19, + "value": "5", + "entity": "time" + }, + { + "start": 12, + "end": 17, + "value": "before", + "entity": "relative-time" + } + ] + }, + { + "text": "when is the chatbot event happening", + "intent": "event-time", + "entities": [ + { + "start": 12, + "end": 19, + "value": "chatbot", + "entity": "event_name" + } + ] + }, + { + "text": "when is python 101 event happening", + "intent": "event-time", + "entities": [ + { + "start": 8, + "end": 18, + "value": "python 101", + "entity": "event_name" + } + ] + }, + { + "text": "what event is happening 2 tomorrow", + "intent": "event-request", + "entities": [ + { + "start": 24, + "end": 25, + "value": "2", + "entity": "time" + }, + { + "start": 26, + "end": 34, + "value": "2", + "entity": "time" + } + ] + } + ] + } +} diff --git a/engine.py b/engine.py new file mode 100644 index 0000000..40fd8cd --- /dev/null +++ b/engine.py @@ -0,0 +1,42 @@ + +##dict of response for each type of intent +intent_response_dict = { + "intro": ["This is a GST FAQ bot. One stop-shop to all your GST related queries"], + "greet":["Hey","Hello","Hi"], + "goodbye":["Bye","It was nice talking to you","See you","ttyl"], + "affirm":["Cool","I know you would like it"] + +} + +gstinfo_response_dict = { + "GST": " Goods and Service Tax (GST) is a destination based tax on consumption of goods and services.", + "benefits":"GST consumes more than a dozen taxes, thus making it hassle free and efficient.", + "faq_link":'You can check all the answers here * { + position: relative; + } + .top-header::before { + content: ''; + position: absolute; + top: -100%; + left: 0; + right: 0; + bottom: -100%; + opacity: 0.25; + background-color: #404040 + } + .chat-box { + list-style: none; + background: #e5e5e5; + margin: 0; + padding: 0 0 50px 0; + height: 280px; + overflow-y: auto; + } + .chat-box li { + padding: 0.5rem; + overflow: hidden; + display: flex; + } + .chat-box .avatar-icon { + width: 40px; + position: relative; + } + .chat-box .avatar-icon img { + display: block; + width: 100%; + background-color:#1469A6; + } + .ibo .avatar-icon:after { + content: ''; + position: absolute; + top: 0; + right: 0; + width: 0; + height: 0; + border: 5px solid white; + border-left-color: transparent; + border-bottom-color: transparent; + } + .me { + justify-content: flex-end; + align-items: flex-end; + } + .me .messages { + order: 1; + border-bottom-right-radius: 0; + } + .me .avatar-icon { + order: 2; + } + .me .avatar-icon:after { + content: ''; + position: absolute; + bottom: 0; + left: 0; + width: 0; + height: 0; + border: 5px solid white; + border-right-color: transparent; + border-top-color: transparent; + box-shadow: 1px 1px 2px rgba(0, 0, 0, 0.2); + } + .messages { + background: white; + padding: 10px; + border-radius: 2px; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.2); + } + .messages p { + font-size: 0.8rem; + margin: 0 0 0.2rem 0; + } + .messages time { + font-size: 0.7rem; + color: #ccc; + } + .setting{ + background-color: #e5e5e5; + height: 32px; + padding-top: 2px; + border-bottom: 1px solid rgba(0,0,0,.1); + } + .setting .left { + float: left; + } + .setting .right { + float: right; + } + .iconicstroke-user{ + font-size: 22px; + position: relative; + top: 4px; + left: 10px; + color: #414141; + cursor:pointer; + } + .typicons-cog{ + font-size: 23px; + position: relative; + top: 7px; + right: 4px; + color: #414141; + cursor:pointer; + } + .fontawesome-facetime-video{ + font-size: 18px; + position: relative; + top: 3px; + color: #414141; + left: 5px; + cursor:pointer; + } + .iconicstroke-user:hover, .typicons-cog:hover,.fontawesome-facetime-video:hover{ + color:#000000; + } + ::-webkit-scrollbar{height:14px;width:10px;background:#eee;border-left:1px solid #ddd} + ::-webkit-scrollbar-thumb{background:#ddd;border:1px solid #cfcfcf} + ::-webkit-scrollbar-thumb:hover{background:#b2b2b2;border:1px solid #b2b2b2} + ::-webkit-scrollbar-thumb:active{background:#b2b2b2;border:1px solid #b2b2b2} + @-webkit-keyframes pulse { + from { + opacity: 0; + } + to { + opacity: 0.5; + } + } + + /************ + * response * + ************/ + #response { + width:320px; + background-color: rgba(255, 255, 255, 0.8); + } + .say { + width:220px; + padding:8px 15px; + background:rgba(50, 50, 50, 0.2); + border:0px solid #dbdbdb; + } + .saybtn { + position:relative; + padding:6px 15px; + left:-8px; + border:2px solid #207cca; + background-color:#207cca; + color:#fafafa; + } + .saybtn:hover { + background-color:#409cea; + } + + .ace_editor { + border: 1px solid lightgray; + margin: auto; + height: 200px; + width: 80%; + } + .scrollmargin { + height: 80px; + text-align: center; + } + .view{ + border: 1px solid lightgray; + margin: auto; + width: 80%; + } + .view div span{ + margin: 20px; + display: inline-block; + } + .view div span span{ + margin: 0px; + display: inline; + } + .output{ + min-height: 70px; + } + .TitleBar { + margin: auto; + width: 80%; + border: 1px solid lightgray; + height: 30px; + border-bottom: 0px; + background-color: #FCFAFA; + font-size:20px; + } + .TitleBar b{ + margin:15px; + color: #454444; + } + .actionbar{ + margin: auto; + width: 80%; + } + #statusBar { + margin: auto; + width: 80%; + border: 1px solid lightgray; + height: 20px; + border-top: 0px; + } + + .ace_status-indicator { + color: gray; + float:right; + right: 0; + border-left: 1px solid; + } + .submit { + float: right; + border: 1px solid #AAA; + margin-left: 10px; + padding: 4px; + cursor: pointer; + } + + .blinking-cursor { + font-weight: 500; + font-size: 15px; + color: #2E3D48; + -webkit-animation: 1s blink step-end infinite; + -moz-animation: 1s blink step-end infinite; + -ms-animation: 1s blink step-end infinite; + -o-animation: 1s blink step-end infinite; + animation: 1s blink step-end infinite; + } + + @keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-moz-keyframes blink { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-webkit-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-ms-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-o-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + #submit:disabled,#SubmitMCQ :disabled { + background-color: white; + } + #submit, #SubmitMCQ { + background: #2cbb0f; + color: white; + } + #submit:hover,#SubmitMCQ:hover{ + background: white; + color: #2cbb0f;} + .submit:hover { + box-shadow: 1px 1px 3px gray; + } + .submit:disabled { + box-shadow: unset; + cursor: unset; + color: lightgrey !important; + background-color: #f6f6f6 !important; + } + #run { + background-color: #4c9ed9; + color: white; + } + #compiler::first-letter { + text-transform: uppercase; + } + @media only screen and (max-height: 480px) { + .chat-box { + height: calc(100vh - 180px); + } + + } + #response{ + width: calc(100% + 20px); + } + @media only screen and (max-Width: 340px) { + .chat-container { + width: calc(100vw - 20px); + max-width: 300px; + margin: auto 10px; + } + .say { + width: calc(100% - 100px); + } + + } + .view { + white-space: pre-wrap; /* Since CSS 2.1 */ + white-space: -moz-pre-wrap; /* Mozilla, since 1999 */ + white-space: -pre-wrap; /* Opera 4-6 */ + white-space: -o-pre-wrap; /* Opera 7 */ + word-wrap: break-word; /* Internet Explorer 5.5+ */ + } + +#QI { + overflow-x: hidden; +} + +.slide { + opacity: 0; + position: relative; + font-family: Arial; + font-size: 14px; + /*line-height: 50px;*/ + right: -100%; + width:100%; +} + +/*.choice { + -webkit-column-count: 2; + -moz-column-count: 2; + column-count: 2; +}*/ +.MCanswer { +display: inline-block; +vertical-align: top; +} + .tab-container{ + background: #f1f1f1; + /* margin: 0; */ + padding: 0; + /* max-height: 35px; */ + /* position: relative; */ + overflow: hidden; +} + +ul.tabs{ + margin: 0; + list-style-type : none; + line-height : 35px; + max-height: 35px; + overflow: hidden; + display: inline-block; + padding: 0; + padding-right: 10px; + padding-left: 10px; + border-bottom: 1px solid #d4d4d4; + width: 100%; +} + +ul.tabs > li.active{ + z-index: 2; + background: white; +} + +ul.tabs > li.active:before{ + border-color : transparent #efefef transparent transparent; +} + + +ul.tabs > li.active:after{ + border-color : transparent transparent transparent #efefef; +} + +ul.tabs > li{ + float: left; + margin : 5px -10px 0; + border-top-right-radius: 25px 170px; + border-top-left-radius: 20px 90px; + padding : 0 30px 0 25px; + height: 170px; + background: #ddd; + position : relative; + box-shadow: 0 10px 20px rgba(0,0,0,.5); + max-width : 200px; +} + +ul.tabs > li > a{ + display: inline-block; + max-width:100%; + overflow: hidden; + text-overflow: ellipsis; + text-decoration: none; + color: #222; +} + +ul.tabs > li:before, ul.tabs > li:after{ + content : ''; + background : transparent; + height: 20px; + width: 20px; + border-radius: 100%; + border-width: 10px; + top: 0px; + border-style : solid; + position : absolute; +} + +ul.tabs > li:before{ + + border-color : transparent #ddd transparent transparent; + left: -23px; + -ms-transform: rotate(48deg); + -webkit-transform : rotate(48deg); + transform: rotate(48deg); +} + +ul.tabs > li:after{ + border-color : transparent transparent transparent #ddd; + -webkit-transform : rotate(-48deg); + -ms-transform: rotate(-48deg); + transform: rotate(-48deg); + right: -17px; +} + +/* Clear Fix took for HTML 5 Boilerlate*/ +.clearfix:after { clear: both; } +.clearfix { zoom: 1; } +.clearfix:after,.clearfix:before{ + -webkit-box-sizing: unset; + -moz-box-sizing: unset; + box-sizing: unset; + } + +*{ + -webkit-box-sizing: unset; + -moz-box-sizing: unset; + box-sizing: unset; +} +body{ + line-height: unset; +} +pre{ + padding: unset; + border-radius:unset; +} +#modal-backdrop{ + height: 100vh; + width: 100vw; + background: rgba(0,0,0,0.53); + z-index: 10000; + position: fixed; + top: 0px; + left: 0px; +} +#modal{ + border-radius: 4px; + background: white; + width: 500px; + margin: auto; + top: 100px; + position: relative; + color: #757575; + overflow: hidden; + +} +#modal-header{ + min-height: 20px; + width: 100%; + font-size: 16px; + font-weight: 100; + border-bottom: 1px solid lightgray; + padding: 12px; + /*text-shadow: 1px 1px 1px rgba(114, 119, 112, 0.8);*/ +} +#modal-body{ + min-height: 20px; + width: 100%; + padding: 5px; + overflow: hidden +} +#modal-footer{ + min-height: 20px; + width: 100%; + border-top: 1px solid lightgray; + padding: 5px; +} +#modal-footer #next{ + cursor: unset; + color: white; + background-color: #4CAF50; + float: right; + margin: 5px; + margin-right: 8px; + border: unset; + padding: 6px; + border-radius: 1px; +} +#modal-footer #next:hover{ + background-color: #ffffff; + color: #4CAF50; + box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2),0 6px 20px 0 rgba(0,0,0,0.19); +} +#modal-footer #skip{ + cursor: unset; + color: white; + background-color: #FF622C; + float: right; + margin: 5px; + margin-right: 8px; + border: unset; + padding: 6px; + border-radius: 1px; +} +#modal-footer #skip:hover{ + background-color: white; + color: #FF622C; + box-shadow: 0 8px 16px 0 rgba(0,0,0,0.2),0 6px 20px 0 rgba(0,0,0,0.19); +} +.skip:disabled { + box-shadow: unset; + cursor: unset; + color: lightgrey !important; + background-color: #f6f6f6 !important; +} +.test-text { + background-color: white; + margin-left: 40px; + margin-right: 479px; + min-height: 58px; + +} +#modal-body div { +float: left; +width: 166px; +display: inline-block; +/* possibly also height: 300px; */ +} +#modal-body div p span { +font-family: serif;} \ No newline at end of file diff --git a/static/css/style.css~ b/static/css/style.css~ new file mode 100644 index 0000000..5a4eabc --- /dev/null +++ b/static/css/style.css~ @@ -0,0 +1,423 @@ + @import url(http://weloveiconfonts.com/api/?family=fontawesome|iconicstroke|typicons); + /* fontawesome */ + [class*="fontawesome-"]:before { + font-family: 'FontAwesome', sans-serif; + } + /* iconicstroke */ + [class*="iconicstroke-"]:before { + font-family: 'IconicStroke', sans-serif; + } + /* typicons */ + [class*="typicons-"]:before { + font-family: 'Typicons', sans-serif; + } + body{ + font-family:arial,sans-serif; + } + .chat-container { + width: 300px; + margin-right: 20px; + float:right; + overflow:hidden; + } + .top-header { + background: #666; + color: white; + padding: 0.2rem; + position: relative; + overflow: hidden; + border-bottom: 4px solid #35ac19; + cursor:pointer; + } + .top-header:hover { + background-color:#35ac19; + } + .top-header-tit { + display: inline; + font-size: 14px; + } + .top-header .typicons-message { + display: inline-block; + padding: 2px 5px 2px 5px; + font-size: 20px; + position: relative; + top: 5px; + } + .top-header .typicons-minus { + position: relative; + top: 3px; + font-size: 15px; + cursor:pointer; + } + .top-header .typicons-plus { + position: relative; + top: 3px; + font-size: 15px; + } + .top-header .typicons-times{ + position: relative; + top: 3px; + font-size: 15px; + } + .top-header .left { + float: left; + } + .top-header .right { + float: right; + padding-top: 5px; + } + .top-header > * { + position: relative; + } + .top-header::before { + content: ''; + position: absolute; + top: -100%; + left: 0; + right: 0; + bottom: -100%; + opacity: 0.25; + background-color: #404040 + } + .chat-box { + list-style: none; + background: #e5e5e5; + margin: 0; + padding: 0 0 50px 0; + height: 280px; + overflow-y: auto; + } + .chat-box li { + padding: 0.5rem; + overflow: hidden; + display: flex; + } + .chat-box .avatar-icon { + width: 40px; + position: relative; + } + .chat-box .avatar-icon img { + display: block; + width: 100%; + background-color:#1469A6; + } + .ibo .avatar-icon:after { + content: ''; + position: absolute; + top: 0; + right: 0; + width: 0; + height: 0; + border: 5px solid white; + border-left-color: transparent; + border-bottom-color: transparent; + } + .me { + justify-content: flex-end; + align-items: flex-end; + } + .me .messages { + order: 1; + border-bottom-right-radius: 0; + } + .me .avatar-icon { + order: 2; + } + .me .avatar-icon:after { + content: ''; + position: absolute; + bottom: 0; + left: 0; + width: 0; + height: 0; + border: 5px solid white; + border-right-color: transparent; + border-top-color: transparent; + box-shadow: 1px 1px 2px rgba(0, 0, 0, 0.2); + } + .messages { + background: white; + padding: 10px; + border-radius: 2px; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.2); + } + .messages p { + font-size: 0.8rem; + margin: 0 0 0.2rem 0; + } + .messages time { + font-size: 0.7rem; + color: #ccc; + } + .setting{ + background-color: #e5e5e5; + height: 32px; + padding-top: 2px; + border-bottom: 1px solid rgba(0,0,0,.1); + } + .setting .left { + float: left; + } + .setting .right { + float: right; + } + .iconicstroke-user{ + font-size: 22px; + position: relative; + top: 4px; + left: 10px; + color: #414141; + cursor:pointer; + } + .typicons-cog{ + font-size: 23px; + position: relative; + top: 7px; + right: 4px; + color: #414141; + cursor:pointer; + } + .fontawesome-facetime-video{ + font-size: 18px; + position: relative; + top: 3px; + color: #414141; + left: 5px; + cursor:pointer; + } + .iconicstroke-user:hover, .typicons-cog:hover,.fontawesome-facetime-video:hover{ + color:#000000; + } + ::-webkit-scrollbar{height:14px;width:10px;background:#eee;border-left:1px solid #ddd} + ::-webkit-scrollbar-thumb{background:#ddd;border:1px solid #cfcfcf} + ::-webkit-scrollbar-thumb:hover{background:#b2b2b2;border:1px solid #b2b2b2} + ::-webkit-scrollbar-thumb:active{background:#b2b2b2;border:1px solid #b2b2b2} + @-webkit-keyframes pulse { + from { + opacity: 0; + } + to { + opacity: 0.5; + } + } + + /************ + * response * + ************/ + #response { + width:320px; + background-color: rgba(255, 255, 255, 0.8); + } + .say { + width:212px; + padding:8px 15px; + background:rgba(50, 50, 50, 0.2); + border:0px solid #dbdbdb; + } + .saybtn { + position:relative; + padding:6px 15px; + left:-8px; + border:2px solid #207cca; + background-color:#207cca; + color:#fafafa; + } + .saybtn:hover { + background-color:#409cea; + } + + .ace_editor { + border: 1px solid lightgray; + margin: auto; + height: 200px; + width: 80%; + } + .scrollmargin { + height: 80px; + text-align: center; + } + .view{ + border: 1px solid lightgray; + margin: auto; + width: 80%; + } + .view div span{ + margin: 20px; + display: inline-block; + } + .view div span span{ + margin: 0px; + display: inline; + } + .output{ + min-height: 70px; + } + .TitleBar { + margin: auto; + width: 80%; + border: 1px solid lightgray; + height: 30px; + border-bottom: 0px; + background-color: #FCFAFA; + font-size:20px; + } + .TitleBar b{ + margin:15px; + color: #454444; + } + .actionbar{ + margin: auto; + width: 80%; + } + #statusBar { + margin: auto; + width: 80%; + border: 1px solid lightgray; + height: 20px; + border-top: 0px; + } + + .ace_status-indicator { + color: gray; + float:right; + right: 0; + border-left: 1px solid; + } + .submit { + float: right; + border: 1px solid #AAA; + margin-left: 10px; + padding: 4px; + cursor: pointer; + } + + + #custominputfileds { + display:none; + } + + .blinking-cursor { + font-weight: 500; + font-size: 15px; + color: #2E3D48; + -webkit-animation: 1s blink step-end infinite; + -moz-animation: 1s blink step-end infinite; + -ms-animation: 1s blink step-end infinite; + -o-animation: 1s blink step-end infinite; + animation: 1s blink step-end infinite; + } + + @keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-moz-keyframes blink { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-webkit-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-ms-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + + @-o-keyframes "blink" { + from, to { + color: transparent; + } + 50% { + color: black; + } + } + #submit:disabled,#SubmitMCQ :disabled { + background-color: white; + } + #submit,#SubmitMCQ { + background: #35ac19; + color: wheat; + } + .submit:hover { + box-shadow: 1px 1px 3px gray; + } + .submit:disabled { + box-shadow: unset; + cursor: unset; + color: lightgrey !important; + background-color: #f6f6f6 !important; + } + #compiler::first-letter { + text-transform: uppercase; + } + @media only screen and (max-height: 480px) { + .chat-box { + height: calc(100vh - 180px); + } + + } + #response{ + width: calc(100% + 20px); + } + @media only screen and (max-Width: 340px) { + .chat-container { + width: calc(100vw - 20px); + max-width: 300px; + margin: auto 10px; + } + .say { + width: calc(100% - 108px); + } + + } + .view { + white-space: pre-wrap; /* Since CSS 2.1 */ + white-space: -moz-pre-wrap; /* Mozilla, since 1999 */ + white-space: -pre-wrap; /* Opera 4-6 */ + white-space: -o-pre-wrap; /* Opera 7 */ + word-wrap: break-word; /* Internet Explorer 5.5+ */ + } + +#QI { + overflow-x: hidden; +} + +.slide { + opacity: 0; + position: relative; + font-family: Arial; + font-size: 14px; + /*line-height: 50px;*/ + right: -100%; + width:100%; +} + +/*.choice { + -webkit-column-count: 2; + -moz-column-count: 2; + column-count: 2; +}*/ +.MCanswer { +display: inline-block; +vertical-align: top; +} diff --git a/static/css/temporary.css b/static/css/temporary.css new file mode 100644 index 0000000..3833590 --- /dev/null +++ b/static/css/temporary.css @@ -0,0 +1,16 @@ +.chat_window{ + margin-left: 50%; + height: calc(100vh - 120px); +} +.messages{ + height: calc(100vh - 250px); +} + +.messages .message.left .text { + color: black !important; + font-weight: inherit; +} + +#msg_input{ + color: black; +} diff --git a/static/js/bind.js b/static/js/bind.js new file mode 100644 index 0000000..01f6d6b --- /dev/null +++ b/static/js/bind.js @@ -0,0 +1,88 @@ +var data=[]; + +function addBr(text){ + return text.replace(/\n/g, "
"); + +} +var Message; +Message = function (arg) { + this.text = arg.text, this.message_side = arg.message_side; + this.draw = function (_this) { + return function () { + var $message; + $message = $($('.message_template').clone().html()); + $message.addClass(_this.message_side).find('.text').html(addBr(_this.text)); + $('.messages').append($message); + return setTimeout(function () { + return $message.addClass('appeared'); + }, 0); + }; + }(this); + return this; +}; + + +function showBotMessage(msg){ + message = new Message({ + text: msg, + message_side: 'left' + }); + message.draw(); + $messages.animate({ scrollTop: $messages.prop('scrollHeight') }, 300); +} +function showUserMessage(msg){ + $messages = $('.messages'); + message = new Message({ + text: msg, + message_side: 'right' + }); + message.draw(); + $messages.animate({ scrollTop: $messages.prop('scrollHeight') }, 300); + $('#msg_input').val(''); +} +function sayToBot(text){ + document.getElementById("msg_input").placeholder = "Type your messages here..." + $.post("/chat", + { + //csrfmiddlewaretoken:csrf, + text:text, + }, + function(jsondata, status){ + if(jsondata["status"]=="success"){ + response=jsondata["response"]; + + if(response){showBotMessage(response);} + } + }); + +} + +getMessageText = function () { + var $message_input; + $message_input = $('.message_input'); + return $message_input.val(); + }; + +$("#say").keypress(function(e) { + if(e.which == 13) { + $("#saybtn").click(); + } +}); + +$('.send_message').click(function (e) { + msg = getMessageText(); + if(msg){ + showUserMessage(msg); + sayToBot(msg); + $('.message_input').val('');} +}); + +$('.message_input').keyup(function (e) { + if (e.which === 13) { + msg = getMessageText(); + if(msg){ + showUserMessage(msg); + sayToBot(msg); + $('.message_input').val('') ;} + } +}); diff --git a/static/js/jquery.timeago.js b/static/js/jquery.timeago.js new file mode 100644 index 0000000..264b731 --- /dev/null +++ b/static/js/jquery.timeago.js @@ -0,0 +1,231 @@ +/** + * Timeago is a jQuery plugin that makes it easy to support automatically + * updating fuzzy timestamps (e.g. "4 minutes ago" or "about 1 day ago"). + * + * @name timeago + * @version 1.5.3 + * @requires jQuery v1.2.3+ + * @author Ryan McGeary + * @license MIT License - http://www.opensource.org/licenses/mit-license.php + * + * For usage and examples, visit: + * http://timeago.yarp.com/ + * + * Copyright (c) 2008-2015, Ryan McGeary (ryan -[at]- mcgeary [*dot*] org) + */ + +(function (factory) { + if (typeof define === 'function' && define.amd) { + // AMD. Register as an anonymous module. + define(['jquery'], factory); + } else if (typeof module === 'object' && typeof module.exports === 'object') { + factory(require('jquery')); + } else { + // Browser globals + factory(jQuery); + } +}(function ($) { + $.timeago = function(timestamp) { + if (timestamp instanceof Date) { + return inWords(timestamp); + } else if (typeof timestamp === "string") { + return inWords($.timeago.parse(timestamp)); + } else if (typeof timestamp === "number") { + return inWords(new Date(timestamp)); + } else { + return inWords($.timeago.datetime(timestamp)); + } + }; + var $t = $.timeago; + + $.extend($.timeago, { + settings: { + refreshMillis: 60000, + allowPast: true, + allowFuture: false, + localeTitle: false, + cutoff: 0, + autoDispose: true, + strings: { + prefixAgo: null, + prefixFromNow: null, + suffixAgo: "ago", + suffixFromNow: "from now", + inPast: 'any moment now', + seconds: "less than a minute", + minute: "about a minute", + minutes: "%d minutes", + hour: "about an hour", + hours: "about %d hours", + day: "a day", + days: "%d days", + month: "about a month", + months: "%d months", + year: "about a year", + years: "%d years", + wordSeparator: " ", + numbers: [] + } + }, + + inWords: function(distanceMillis) { + if (!this.settings.allowPast && ! this.settings.allowFuture) { + throw 'timeago allowPast and allowFuture settings can not both be set to false.'; + } + + var $l = this.settings.strings; + var prefix = $l.prefixAgo; + var suffix = $l.suffixAgo; + if (this.settings.allowFuture) { + if (distanceMillis < 0) { + prefix = $l.prefixFromNow; + suffix = $l.suffixFromNow; + } + } + + if (!this.settings.allowPast && distanceMillis >= 0) { + return this.settings.strings.inPast; + } + + var seconds = Math.abs(distanceMillis) / 1000; + var minutes = seconds / 60; + var hours = minutes / 60; + var days = hours / 24; + var years = days / 365; + + function substitute(stringOrFunction, number) { + var string = $.isFunction(stringOrFunction) ? stringOrFunction(number, distanceMillis) : stringOrFunction; + var value = ($l.numbers && $l.numbers[number]) || number; + return string.replace(/%d/i, value); + } + + var words = seconds < 45 && substitute($l.seconds, Math.round(seconds)) || + seconds < 90 && substitute($l.minute, 1) || + minutes < 45 && substitute($l.minutes, Math.round(minutes)) || + minutes < 90 && substitute($l.hour, 1) || + hours < 24 && substitute($l.hours, Math.round(hours)) || + hours < 42 && substitute($l.day, 1) || + days < 30 && substitute($l.days, Math.round(days)) || + days < 45 && substitute($l.month, 1) || + days < 365 && substitute($l.months, Math.round(days / 30)) || + years < 1.5 && substitute($l.year, 1) || + substitute($l.years, Math.round(years)); + + var separator = $l.wordSeparator || ""; + if ($l.wordSeparator === undefined) { separator = " "; } + return $.trim([prefix, words, suffix].join(separator)); + }, + + parse: function(iso8601) { + var s = $.trim(iso8601); + s = s.replace(/\.\d+/,""); // remove milliseconds + s = s.replace(/-/,"/").replace(/-/,"/"); + s = s.replace(/T/," ").replace(/Z/," UTC"); + s = s.replace(/([\+\-]\d\d)\:?(\d\d)/," $1$2"); // -04:00 -> -0400 + s = s.replace(/([\+\-]\d\d)$/," $100"); // +09 -> +0900 + return new Date(s); + }, + datetime: function(elem) { + var iso8601 = $t.isTime(elem) ? $(elem).attr("datetime") : $(elem).attr("title"); + return $t.parse(iso8601); + }, + isTime: function(elem) { + // jQuery's `is()` doesn't play well with HTML5 in IE + return $(elem).get(0).tagName.toLowerCase() === "time"; // $(elem).is("time"); + } + }); + + // functions that can be called via $(el).timeago('action') + // init is default when no action is given + // functions are called with context of a single element + var functions = { + init: function() { + var refresh_el = $.proxy(refresh, this); + refresh_el(); + var $s = $t.settings; + if ($s.refreshMillis > 0) { + this._timeagoInterval = setInterval(refresh_el, $s.refreshMillis); + } + }, + update: function(timestamp) { + var date = (timestamp instanceof Date) ? timestamp : $t.parse(timestamp); + $(this).data('timeago', { datetime: date }); + if ($t.settings.localeTitle) { + $(this).attr("title", date.toLocaleString()); + } + refresh.apply(this); + }, + updateFromDOM: function() { + $(this).data('timeago', { datetime: $t.parse( $t.isTime(this) ? $(this).attr("datetime") : $(this).attr("title") ) }); + refresh.apply(this); + }, + dispose: function () { + if (this._timeagoInterval) { + window.clearInterval(this._timeagoInterval); + this._timeagoInterval = null; + } + } + }; + + $.fn.timeago = function(action, options) { + var fn = action ? functions[action] : functions.init; + if (!fn) { + throw new Error("Unknown function name '"+ action +"' for timeago"); + } + // each over objects here and call the requested function + this.each(function() { + fn.call(this, options); + }); + return this; + }; + + function refresh() { + var $s = $t.settings; + + //check if it's still visible + if ($s.autoDispose && !$.contains(document.documentElement,this)) { + //stop if it has been removed + $(this).timeago("dispose"); + return this; + } + + var data = prepareData(this); + + if (!isNaN(data.datetime)) { + if ( $s.cutoff === 0 || Math.abs(distance(data.datetime)) < $s.cutoff) { + $(this).text(inWords(data.datetime)); + } else { + if ($(this).attr('title').length > 0) { + $(this).text($(this).attr('title')); + } + } + } + return this; + } + + function prepareData(element) { + element = $(element); + if (!element.data("timeago")) { + element.data("timeago", { datetime: $t.datetime(element) }); + var text = $.trim(element.text()); + if ($t.settings.localeTitle) { + element.attr("title", element.data('timeago').datetime.toLocaleString()); + } else if (text.length > 0 && !($t.isTime(element) && element.attr("title"))) { + element.attr("title", text); + } + } + return element.data("timeago"); + } + + function inWords(date) { + return $t.inWords(distance(date)); + } + + function distance(date) { + return (new Date().getTime() - date.getTime()); + } + + // fix for IE6 suckage + document.createElement("abbr"); + document.createElement("time"); +})); diff --git a/templates/base.html b/templates/base.html new file mode 100644 index 0000000..6cf86c8 --- /dev/null +++ b/templates/base.html @@ -0,0 +1,29 @@ + + + + + + + + + + + + + + + +{% block header %}{% endblock %} + + + +

GST FAQ Chat

+
+ {% block content %}{% endblock %} +
+ + + + diff --git a/templates/home.html b/templates/home.html new file mode 100644 index 0000000..5365a83 --- /dev/null +++ b/templates/home.html @@ -0,0 +1,40 @@ +{% extends "base.html" %} + +{% block header %} + + + +{% endblock %} + +{% block content %} +
+
+
+
+
    +
    +
    + +
    +
    +
    send
    +
    +
    +
    +
    +
  • +
    +
    +
    +
    +
  • +
    +
    +
    +
    + +{% endblock %} + +{% block other_footers %} + +{% endblock %}