了解 RASA 表格

Understanding RASA Forms

我的目标:

我正在尝试使用 Forms 为我的 RASA 助手实施一个简单的报告规则,它应该按如下方式工作:

User: "I want to report something."
Assistant: "Please describe your problem in the following message."
User: <short description of problem>
Assistant: "Thank you for report."

我希望,来自用户的整个报告消息将作为文本(字符串)保存在 report_message 槽中,这也是我的主要目标。我遵循了官方 RASA 文档,可能遗漏了一些重要的东西或在某处制造了错误,但我找不到我做错了什么。

当前状态:

当前的实现是这样的:

User: "I want to report something."
Assistant: "Thank you for report."

Assistant 完全忽略 utter_ask_report_message 并且 report_message 槽中填满了我的 report 意图的文本内容 - I want to report something..

我的 RASA 项目文件:

nlu.yml

version: "2.0"

nlu:
  - intent: report
    examples: |
      - I want to report something.
      - I want to report a problem.
      - I want to report a bug.
      - #report

rules.yml

version: "2.0"

rules:
  - rule: Activate report_message_form
    steps:
      - intent: report
      - action: report_message_form
      - active_loop: report_message_form

  - rule: Submit report_message_form
    condition:
      - active_loop: report_message_form
    steps:
      - action: report_message_form
      - active_loop: null
      - slot_was_set:
          - requested_slot: null
      - action: utter_success_report_message_form

domain.yml

version: "2.0"

actions:
  - validate_report_message_form

intents:
  - report

entities:
  - report_message

slots:
  report_message:
    type: text

forms:
  report_message_form:
    report_message:
      - type: from_text
        intent: report

responses:
  utter_ask_report_message:
    - text: "Please describe your problem in the following message."

  utter_success_report_message_form:
    - text: "Thank you for report."

actions.py

from typing import Dict, Text, List, Optional, Any

from rasa_sdk import Tracker
from rasa_sdk.executor import CollectingDispatcher
from rasa_sdk.forms import FormValidationAction
from rasa_sdk.types import DomainDict


class ValidateReportMessageForm(FormValidationAction):
    def name(self) -> Text:
        return "validate_report_message_form"

    async def required_slots(
        self,
        slots_mapped_in_domain: List[Text],
        dispatcher: CollectingDispatcher,
        tracker: Tracker,
        domain: DomainDict
    ) -> Optional[List[Text]]:
        return slots_mapped_in_domain + ["report_message"]

    async def extract_report_message(
        self,
        dispatcher: CollectingDispatcher,
        tracker: Tracker,
        domain: Dict
    ) -> Dict[Text, Any]:
        text_of_last_user_message = tracker.latest_message.get("text")
        return {"report_message": text_of_last_user_message}

感谢您的每一个帮助和建议。

问题是您对 validate_report_message_form 的实施。在激活表单期间也会调用此操作,这意味着 extract_report_message 将用激活表单的消息文本填充它。您可以通过添加 if tracker.slots["requested_slot"] == "report_message" 的检查来解决此问题,以确保仅在 Rasa Open Source 请求用户填充插槽时才设置此插槽。

from typing import Dict, Text, List, Optional, Any

from rasa_sdk import Tracker
from rasa_sdk.executor import CollectingDispatcher
from rasa_sdk.forms import FormValidationAction
from rasa_sdk.types import DomainDict


class ValidateReportMessageForm(FormValidationAction):
    def name(self) -> Text:
        return "validate_report_message_form"

    async def required_slots(
        self,
        slots_mapped_in_domain: List[Text],
        dispatcher: CollectingDispatcher,
        tracker: Tracker,
        domain: DomainDict
    ) -> Optional[List[Text]]:
        return slots_mapped_in_domain + ["report_message"]

    async def extract_report_message(
        self,
        dispatcher: CollectingDispatcher,
        tracker: Tracker,
        domain: Dict
    ) -> Dict[Text, Any]:
        if not tracker.slots["requested_slot"] == "report_message":
          return {}

        text_of_last_user_message = tracker.latest_message.get("text")
        return {"report_message": text_of_last_user_message}