| import openai | |
| import os | |
| import questionnaires | |
| initial_message = "Hi! I'm Brainy, a virtual assistant who can help you through the mental health screening process. Can you start by telling me a bit about the problems you are experiencing?" | |
| services = "https://www.canada.ca/en/public-health/topics/mental-health-wellness.html" | |
| openai.api_key = os.getenv("OPENAI_API_KEY") | |
| available_questionnaires = list(questionnaires.topics) | |
| def listify(options: list, lower=True): | |
| if len(options) > 1: options[-1] = "and " + options[-1] | |
| if lower is True: options = list(map(str.lower, options)) | |
| return ", ".join(options) if len(options) > 2 else " ".join(options) | |
| def content_summarizer(): | |
| pass | |
| def assess_response(question: str, response:str, options: list, uses_scale=True, context="a psychological evaluation"): | |
| context_prompt = "" if context=="" else f"The context of this discussion is {context}. " | |
| if uses_scale is True: | |
| prompt = context_prompt + f""" | |
| Given the question '{question}' and this response to the question '{response}', rate the response on the following scale: {", ".join(map("'{}'".format, options))}. | |
| Return only the corresponding scale item and nothing else. | |
| """ | |
| else: | |
| prompt = context_prompt + f""" | |
| Given the question '{question}' and this response to the question '{response}', which of the following is the response most similar to? {", ".join(map("'{}'".format, options))}. | |
| Return only the most similar item and nothing else. | |
| """ | |
| response = openai.Completion.create( | |
| model="text-davinci-003", | |
| prompt=prompt, | |
| temperature=0.1, | |
| max_tokens=10 | |
| ) | |
| return response.choices[0].text.strip() | |
| def yes_no(message): | |
| return assess_response(question="Yes or No?", response=message, options=["Yes", "No"], context="", uses_scale=False) | |
| def questionnaire_chooser(message): | |
| topic = assess_response( | |
| question = initial_message, | |
| response = message, | |
| options = available_questionnaires + ["Suicidal", "None of the previously mentioned options"], | |
| uses_scale = False | |
| ) | |
| match topic.lower(): | |
| case "suicidal": | |
| state = ["initial"] | |
| response = f""" | |
| It sounds like you are in a crisis, or require immediate assistance. If this is the case, please call 911. | |
| If would like to know more, resources can be found here: {services}. | |
| """ | |
| case "none of the previously mentioned options": | |
| state = ["initial"] | |
| response = f""" | |
| At the moment I can only help with {listify(available_questionnaires)}. | |
| If you are in a crisis, or require immediate assistance, please call 911. | |
| If you are looking for help with another mental health topic, more resources can be found here: {services}. | |
| """ | |
| case _: | |
| state = ["potential", topic.lower()] | |
| response = f"It sounds like you're having trouble with {topic.lower()}. Is that correct?" | |
| return state, response | |
| def bot_response(next_question=None): | |
| pass | |
| def get_question(questionnaire, number): | |
| print(questionnaire, number) | |
| return questionnaires.questions[questionnaire][number] | |
| def generate_response(user, message): | |
| user_id, state = user["user_id"], user["state"] | |
| match state[0]: | |
| case "initial": | |
| state, response = questionnaire_chooser(message) | |
| case "potential": | |
| if yes_no(message) == "Yes": | |
| state = ["screening", state[1], 1] | |
| response = get_question(state[1], 0) | |
| else: | |
| state, response = ["initial"], "I think I misunderstood you. Let's try again... can you please tell me about the problems you are experiencing?" | |
| case "screening": | |
| state, question = state, get_question(state[1], state[2]) | |
| if question == questionnaires.END: | |
| state = ["finished"] | |
| response = f"I have finished my evaluation, and that is all I can do for you today. Please refresh my page if you would like to start again. If you would like to give your clinician access to my assessment, please give them reference number #{user_id}." | |
| else: | |
| state[2] += 1 | |
| response = question | |
| case "finished": | |
| state, response = state, None | |
| return state, response |