rasa-pro 3.8.16__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of rasa-pro might be problematic. Click here for more details.
- README.md +380 -0
- rasa/__init__.py +10 -0
- rasa/__main__.py +151 -0
- rasa/anonymization/__init__.py +2 -0
- rasa/anonymization/anonymisation_rule_yaml_reader.py +91 -0
- rasa/anonymization/anonymization_pipeline.py +287 -0
- rasa/anonymization/anonymization_rule_executor.py +260 -0
- rasa/anonymization/anonymization_rule_orchestrator.py +120 -0
- rasa/anonymization/schemas/config.yml +47 -0
- rasa/anonymization/utils.py +117 -0
- rasa/api.py +146 -0
- rasa/cli/__init__.py +5 -0
- rasa/cli/arguments/__init__.py +0 -0
- rasa/cli/arguments/data.py +81 -0
- rasa/cli/arguments/default_arguments.py +165 -0
- rasa/cli/arguments/evaluate.py +65 -0
- rasa/cli/arguments/export.py +51 -0
- rasa/cli/arguments/interactive.py +74 -0
- rasa/cli/arguments/run.py +204 -0
- rasa/cli/arguments/shell.py +13 -0
- rasa/cli/arguments/test.py +211 -0
- rasa/cli/arguments/train.py +263 -0
- rasa/cli/arguments/visualize.py +34 -0
- rasa/cli/arguments/x.py +30 -0
- rasa/cli/data.py +292 -0
- rasa/cli/e2e_test.py +566 -0
- rasa/cli/evaluate.py +222 -0
- rasa/cli/export.py +251 -0
- rasa/cli/inspect.py +63 -0
- rasa/cli/interactive.py +164 -0
- rasa/cli/license.py +65 -0
- rasa/cli/markers.py +78 -0
- rasa/cli/project_templates/__init__.py +0 -0
- rasa/cli/project_templates/calm/actions/__init__.py +0 -0
- rasa/cli/project_templates/calm/actions/action_template.py +27 -0
- rasa/cli/project_templates/calm/actions/add_contact.py +30 -0
- rasa/cli/project_templates/calm/actions/db.py +57 -0
- rasa/cli/project_templates/calm/actions/list_contacts.py +22 -0
- rasa/cli/project_templates/calm/actions/remove_contact.py +35 -0
- rasa/cli/project_templates/calm/config.yml +12 -0
- rasa/cli/project_templates/calm/credentials.yml +33 -0
- rasa/cli/project_templates/calm/data/flows/add_contact.yml +31 -0
- rasa/cli/project_templates/calm/data/flows/list_contacts.yml +14 -0
- rasa/cli/project_templates/calm/data/flows/remove_contact.yml +29 -0
- rasa/cli/project_templates/calm/db/contacts.json +10 -0
- rasa/cli/project_templates/calm/domain/add_contact.yml +33 -0
- rasa/cli/project_templates/calm/domain/list_contacts.yml +14 -0
- rasa/cli/project_templates/calm/domain/remove_contact.yml +31 -0
- rasa/cli/project_templates/calm/domain/shared.yml +5 -0
- rasa/cli/project_templates/calm/e2e_tests/cancelations/user_cancels_during_a_correction.yml +16 -0
- rasa/cli/project_templates/calm/e2e_tests/cancelations/user_changes_mind_on_a_whim.yml +7 -0
- rasa/cli/project_templates/calm/e2e_tests/corrections/user_corrects_contact_handle.yml +20 -0
- rasa/cli/project_templates/calm/e2e_tests/corrections/user_corrects_contact_name.yml +19 -0
- rasa/cli/project_templates/calm/e2e_tests/happy_paths/user_adds_contact_to_their_list.yml +15 -0
- rasa/cli/project_templates/calm/e2e_tests/happy_paths/user_lists_contacts.yml +5 -0
- rasa/cli/project_templates/calm/e2e_tests/happy_paths/user_removes_contact.yml +11 -0
- rasa/cli/project_templates/calm/e2e_tests/happy_paths/user_removes_contact_from_list.yml +12 -0
- rasa/cli/project_templates/calm/endpoints.yml +45 -0
- rasa/cli/project_templates/default/actions/__init__.py +0 -0
- rasa/cli/project_templates/default/actions/actions.py +27 -0
- rasa/cli/project_templates/default/config.yml +44 -0
- rasa/cli/project_templates/default/credentials.yml +33 -0
- rasa/cli/project_templates/default/data/nlu.yml +91 -0
- rasa/cli/project_templates/default/data/rules.yml +13 -0
- rasa/cli/project_templates/default/data/stories.yml +30 -0
- rasa/cli/project_templates/default/domain.yml +34 -0
- rasa/cli/project_templates/default/endpoints.yml +42 -0
- rasa/cli/project_templates/default/tests/test_stories.yml +91 -0
- rasa/cli/project_templates/tutorial/actions.py +22 -0
- rasa/cli/project_templates/tutorial/config.yml +11 -0
- rasa/cli/project_templates/tutorial/credentials.yml +33 -0
- rasa/cli/project_templates/tutorial/data/flows.yml +8 -0
- rasa/cli/project_templates/tutorial/domain.yml +17 -0
- rasa/cli/project_templates/tutorial/endpoints.yml +45 -0
- rasa/cli/run.py +136 -0
- rasa/cli/scaffold.py +268 -0
- rasa/cli/shell.py +141 -0
- rasa/cli/studio/__init__.py +0 -0
- rasa/cli/studio/download.py +51 -0
- rasa/cli/studio/studio.py +110 -0
- rasa/cli/studio/train.py +59 -0
- rasa/cli/studio/upload.py +85 -0
- rasa/cli/telemetry.py +90 -0
- rasa/cli/test.py +280 -0
- rasa/cli/train.py +260 -0
- rasa/cli/utils.py +453 -0
- rasa/cli/visualize.py +40 -0
- rasa/cli/x.py +205 -0
- rasa/constants.py +37 -0
- rasa/core/__init__.py +17 -0
- rasa/core/actions/__init__.py +0 -0
- rasa/core/actions/action.py +1450 -0
- rasa/core/actions/action_clean_stack.py +59 -0
- rasa/core/actions/action_run_slot_rejections.py +207 -0
- rasa/core/actions/action_trigger_chitchat.py +31 -0
- rasa/core/actions/action_trigger_flow.py +109 -0
- rasa/core/actions/action_trigger_search.py +31 -0
- rasa/core/actions/constants.py +2 -0
- rasa/core/actions/forms.py +737 -0
- rasa/core/actions/loops.py +111 -0
- rasa/core/actions/two_stage_fallback.py +186 -0
- rasa/core/agent.py +557 -0
- rasa/core/auth_retry_tracker_store.py +122 -0
- rasa/core/brokers/__init__.py +0 -0
- rasa/core/brokers/broker.py +126 -0
- rasa/core/brokers/file.py +58 -0
- rasa/core/brokers/kafka.py +322 -0
- rasa/core/brokers/pika.py +387 -0
- rasa/core/brokers/sql.py +86 -0
- rasa/core/channels/__init__.py +55 -0
- rasa/core/channels/audiocodes.py +463 -0
- rasa/core/channels/botframework.py +339 -0
- rasa/core/channels/callback.py +85 -0
- rasa/core/channels/channel.py +419 -0
- rasa/core/channels/console.py +243 -0
- rasa/core/channels/development_inspector.py +93 -0
- rasa/core/channels/facebook.py +422 -0
- rasa/core/channels/hangouts.py +335 -0
- rasa/core/channels/inspector/.eslintrc.cjs +25 -0
- rasa/core/channels/inspector/.gitignore +23 -0
- rasa/core/channels/inspector/README.md +54 -0
- rasa/core/channels/inspector/assets/favicon.ico +0 -0
- rasa/core/channels/inspector/assets/rasa-chat.js +2 -0
- rasa/core/channels/inspector/custom.d.ts +3 -0
- rasa/core/channels/inspector/dist/assets/arc-5623b6dc.js +1 -0
- rasa/core/channels/inspector/dist/assets/array-9f3ba611.js +1 -0
- rasa/core/channels/inspector/dist/assets/c4Diagram-d0fbc5ce-685c106a.js +10 -0
- rasa/core/channels/inspector/dist/assets/classDiagram-936ed81e-8cbed007.js +2 -0
- rasa/core/channels/inspector/dist/assets/classDiagram-v2-c3cb15f1-5889cf12.js +2 -0
- rasa/core/channels/inspector/dist/assets/createText-62fc7601-24c249d7.js +7 -0
- rasa/core/channels/inspector/dist/assets/edges-f2ad444c-7dd06a75.js +4 -0
- rasa/core/channels/inspector/dist/assets/erDiagram-9d236eb7-62c1e54c.js +51 -0
- rasa/core/channels/inspector/dist/assets/flowDb-1972c806-ce49b86f.js +6 -0
- rasa/core/channels/inspector/dist/assets/flowDiagram-7ea5b25a-4067e48f.js +4 -0
- rasa/core/channels/inspector/dist/assets/flowDiagram-v2-855bc5b3-85583a23.js +1 -0
- rasa/core/channels/inspector/dist/assets/flowchart-elk-definition-abe16c3d-59fe4051.js +139 -0
- rasa/core/channels/inspector/dist/assets/ganttDiagram-9b5ea136-47e3a43b.js +266 -0
- rasa/core/channels/inspector/dist/assets/gitGraphDiagram-99d0ae7c-5a2ac0d9.js +70 -0
- rasa/core/channels/inspector/dist/assets/ibm-plex-mono-v4-latin-regular-128cfa44.ttf +0 -0
- rasa/core/channels/inspector/dist/assets/ibm-plex-mono-v4-latin-regular-21dbcb97.woff +0 -0
- rasa/core/channels/inspector/dist/assets/ibm-plex-mono-v4-latin-regular-222b5e26.svg +329 -0
- rasa/core/channels/inspector/dist/assets/ibm-plex-mono-v4-latin-regular-9ad89b2a.woff2 +0 -0
- rasa/core/channels/inspector/dist/assets/index-268a75c0.js +1040 -0
- rasa/core/channels/inspector/dist/assets/index-2c4b9a3b-dfb8efc4.js +1 -0
- rasa/core/channels/inspector/dist/assets/index-3ee28881.css +1 -0
- rasa/core/channels/inspector/dist/assets/infoDiagram-736b4530-b0c470f2.js +7 -0
- rasa/core/channels/inspector/dist/assets/init-77b53fdd.js +1 -0
- rasa/core/channels/inspector/dist/assets/journeyDiagram-df861f2b-2edb829a.js +139 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-700-60c05ee4.woff +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-700-8335d9b8.svg +438 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-700-9cc39c75.ttf +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-700-ead13ccf.woff2 +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-regular-16705655.woff2 +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-regular-5aeb07f9.woff +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-regular-9c459044.ttf +0 -0
- rasa/core/channels/inspector/dist/assets/lato-v14-latin-regular-9e2898a4.svg +435 -0
- rasa/core/channels/inspector/dist/assets/layout-b6873d69.js +1 -0
- rasa/core/channels/inspector/dist/assets/line-1efc5781.js +1 -0
- rasa/core/channels/inspector/dist/assets/linear-661e9b94.js +1 -0
- rasa/core/channels/inspector/dist/assets/mindmap-definition-beec6740-2d2e727f.js +109 -0
- rasa/core/channels/inspector/dist/assets/ordinal-ba9b4969.js +1 -0
- rasa/core/channels/inspector/dist/assets/path-53f90ab3.js +1 -0
- rasa/core/channels/inspector/dist/assets/pieDiagram-dbbf0591-9d3ea93d.js +35 -0
- rasa/core/channels/inspector/dist/assets/quadrantDiagram-4d7f4fd6-06a178a2.js +7 -0
- rasa/core/channels/inspector/dist/assets/requirementDiagram-6fc4c22a-0bfedffc.js +52 -0
- rasa/core/channels/inspector/dist/assets/sankeyDiagram-8f13d901-d76d0a04.js +8 -0
- rasa/core/channels/inspector/dist/assets/sequenceDiagram-b655622a-37bb4341.js +122 -0
- rasa/core/channels/inspector/dist/assets/stateDiagram-59f0c015-f52f7f57.js +1 -0
- rasa/core/channels/inspector/dist/assets/stateDiagram-v2-2b26beab-4a986a20.js +1 -0
- rasa/core/channels/inspector/dist/assets/styles-080da4f6-7dd9ae12.js +110 -0
- rasa/core/channels/inspector/dist/assets/styles-3dcbcfbf-46e1ca14.js +159 -0
- rasa/core/channels/inspector/dist/assets/styles-9c745c82-4a97439a.js +207 -0
- rasa/core/channels/inspector/dist/assets/svgDrawCommon-4835440b-823917a3.js +1 -0
- rasa/core/channels/inspector/dist/assets/timeline-definition-5b62e21b-9ea72896.js +61 -0
- rasa/core/channels/inspector/dist/assets/xychartDiagram-2b33534f-b631a8b6.js +7 -0
- rasa/core/channels/inspector/dist/index.html +39 -0
- rasa/core/channels/inspector/index.html +37 -0
- rasa/core/channels/inspector/jest.config.ts +13 -0
- rasa/core/channels/inspector/package.json +48 -0
- rasa/core/channels/inspector/setupTests.ts +2 -0
- rasa/core/channels/inspector/src/App.tsx +170 -0
- rasa/core/channels/inspector/src/components/DiagramFlow.tsx +97 -0
- rasa/core/channels/inspector/src/components/DialogueInformation.tsx +187 -0
- rasa/core/channels/inspector/src/components/DialogueStack.tsx +151 -0
- rasa/core/channels/inspector/src/components/ExpandIcon.tsx +16 -0
- rasa/core/channels/inspector/src/components/FullscreenButton.tsx +45 -0
- rasa/core/channels/inspector/src/components/LoadingSpinner.tsx +19 -0
- rasa/core/channels/inspector/src/components/NoActiveFlow.tsx +21 -0
- rasa/core/channels/inspector/src/components/RasaLogo.tsx +32 -0
- rasa/core/channels/inspector/src/components/SaraDiagrams.tsx +39 -0
- rasa/core/channels/inspector/src/components/Slots.tsx +91 -0
- rasa/core/channels/inspector/src/components/Welcome.tsx +54 -0
- rasa/core/channels/inspector/src/helpers/formatters.test.ts +385 -0
- rasa/core/channels/inspector/src/helpers/formatters.ts +239 -0
- rasa/core/channels/inspector/src/helpers/utils.ts +42 -0
- rasa/core/channels/inspector/src/main.tsx +13 -0
- rasa/core/channels/inspector/src/theme/Button/Button.ts +29 -0
- rasa/core/channels/inspector/src/theme/Heading/Heading.ts +31 -0
- rasa/core/channels/inspector/src/theme/Input/Input.ts +27 -0
- rasa/core/channels/inspector/src/theme/Link/Link.ts +10 -0
- rasa/core/channels/inspector/src/theme/Modal/Modal.ts +47 -0
- rasa/core/channels/inspector/src/theme/Table/Table.tsx +38 -0
- rasa/core/channels/inspector/src/theme/Tooltip/Tooltip.ts +12 -0
- rasa/core/channels/inspector/src/theme/base/breakpoints.ts +8 -0
- rasa/core/channels/inspector/src/theme/base/colors.ts +88 -0
- rasa/core/channels/inspector/src/theme/base/fonts/fontFaces.css +29 -0
- rasa/core/channels/inspector/src/theme/base/fonts/ibm-plex-mono-v4-latin/ibm-plex-mono-v4-latin-regular.eot +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/ibm-plex-mono-v4-latin/ibm-plex-mono-v4-latin-regular.svg +329 -0
- rasa/core/channels/inspector/src/theme/base/fonts/ibm-plex-mono-v4-latin/ibm-plex-mono-v4-latin-regular.ttf +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/ibm-plex-mono-v4-latin/ibm-plex-mono-v4-latin-regular.woff +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/ibm-plex-mono-v4-latin/ibm-plex-mono-v4-latin-regular.woff2 +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-700.eot +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-700.svg +438 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-700.ttf +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-700.woff +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-700.woff2 +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-regular.eot +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-regular.svg +435 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-regular.ttf +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-regular.woff +0 -0
- rasa/core/channels/inspector/src/theme/base/fonts/lato-v14-latin/lato-v14-latin-regular.woff2 +0 -0
- rasa/core/channels/inspector/src/theme/base/radii.ts +9 -0
- rasa/core/channels/inspector/src/theme/base/shadows.ts +7 -0
- rasa/core/channels/inspector/src/theme/base/sizes.ts +7 -0
- rasa/core/channels/inspector/src/theme/base/space.ts +15 -0
- rasa/core/channels/inspector/src/theme/base/styles.ts +13 -0
- rasa/core/channels/inspector/src/theme/base/typography.ts +24 -0
- rasa/core/channels/inspector/src/theme/base/zIndices.ts +19 -0
- rasa/core/channels/inspector/src/theme/index.ts +101 -0
- rasa/core/channels/inspector/src/types.ts +64 -0
- rasa/core/channels/inspector/src/vite-env.d.ts +1 -0
- rasa/core/channels/inspector/tests/__mocks__/fileMock.ts +1 -0
- rasa/core/channels/inspector/tests/__mocks__/matchMedia.ts +16 -0
- rasa/core/channels/inspector/tests/__mocks__/styleMock.ts +1 -0
- rasa/core/channels/inspector/tests/renderWithProviders.tsx +14 -0
- rasa/core/channels/inspector/tsconfig.json +26 -0
- rasa/core/channels/inspector/tsconfig.node.json +10 -0
- rasa/core/channels/inspector/vite.config.ts +8 -0
- rasa/core/channels/inspector/yarn.lock +6156 -0
- rasa/core/channels/mattermost.py +229 -0
- rasa/core/channels/rasa_chat.py +126 -0
- rasa/core/channels/rest.py +210 -0
- rasa/core/channels/rocketchat.py +175 -0
- rasa/core/channels/slack.py +620 -0
- rasa/core/channels/socketio.py +274 -0
- rasa/core/channels/telegram.py +298 -0
- rasa/core/channels/twilio.py +169 -0
- rasa/core/channels/twilio_voice.py +367 -0
- rasa/core/channels/vier_cvg.py +374 -0
- rasa/core/channels/webexteams.py +135 -0
- rasa/core/concurrent_lock_store.py +210 -0
- rasa/core/constants.py +107 -0
- rasa/core/evaluation/__init__.py +0 -0
- rasa/core/evaluation/marker.py +267 -0
- rasa/core/evaluation/marker_base.py +925 -0
- rasa/core/evaluation/marker_stats.py +294 -0
- rasa/core/evaluation/marker_tracker_loader.py +103 -0
- rasa/core/exceptions.py +29 -0
- rasa/core/exporter.py +284 -0
- rasa/core/featurizers/__init__.py +0 -0
- rasa/core/featurizers/precomputation.py +410 -0
- rasa/core/featurizers/single_state_featurizer.py +402 -0
- rasa/core/featurizers/tracker_featurizers.py +1172 -0
- rasa/core/http_interpreter.py +89 -0
- rasa/core/information_retrieval/__init__.py +0 -0
- rasa/core/information_retrieval/faiss.py +116 -0
- rasa/core/information_retrieval/information_retrieval.py +72 -0
- rasa/core/information_retrieval/milvus.py +59 -0
- rasa/core/information_retrieval/qdrant.py +102 -0
- rasa/core/jobs.py +63 -0
- rasa/core/lock.py +139 -0
- rasa/core/lock_store.py +344 -0
- rasa/core/migrate.py +404 -0
- rasa/core/nlg/__init__.py +3 -0
- rasa/core/nlg/callback.py +147 -0
- rasa/core/nlg/contextual_response_rephraser.py +270 -0
- rasa/core/nlg/generator.py +230 -0
- rasa/core/nlg/interpolator.py +143 -0
- rasa/core/nlg/response.py +155 -0
- rasa/core/nlg/summarize.py +69 -0
- rasa/core/policies/__init__.py +0 -0
- rasa/core/policies/ensemble.py +329 -0
- rasa/core/policies/enterprise_search_policy.py +717 -0
- rasa/core/policies/enterprise_search_prompt_template.jinja2 +62 -0
- rasa/core/policies/flow_policy.py +205 -0
- rasa/core/policies/flows/__init__.py +0 -0
- rasa/core/policies/flows/flow_exceptions.py +44 -0
- rasa/core/policies/flows/flow_executor.py +582 -0
- rasa/core/policies/flows/flow_step_result.py +43 -0
- rasa/core/policies/intentless_policy.py +924 -0
- rasa/core/policies/intentless_prompt_template.jinja2 +22 -0
- rasa/core/policies/memoization.py +538 -0
- rasa/core/policies/policy.py +716 -0
- rasa/core/policies/rule_policy.py +1276 -0
- rasa/core/policies/ted_policy.py +2146 -0
- rasa/core/policies/unexpected_intent_policy.py +1015 -0
- rasa/core/processor.py +1331 -0
- rasa/core/run.py +315 -0
- rasa/core/secrets_manager/__init__.py +0 -0
- rasa/core/secrets_manager/constants.py +32 -0
- rasa/core/secrets_manager/endpoints.py +391 -0
- rasa/core/secrets_manager/factory.py +233 -0
- rasa/core/secrets_manager/secret_manager.py +262 -0
- rasa/core/secrets_manager/vault.py +576 -0
- rasa/core/test.py +1337 -0
- rasa/core/tracker_store.py +1664 -0
- rasa/core/train.py +107 -0
- rasa/core/training/__init__.py +89 -0
- rasa/core/training/converters/__init__.py +0 -0
- rasa/core/training/converters/responses_prefix_converter.py +119 -0
- rasa/core/training/interactive.py +1742 -0
- rasa/core/training/story_conflict.py +381 -0
- rasa/core/training/training.py +93 -0
- rasa/core/utils.py +344 -0
- rasa/core/visualize.py +70 -0
- rasa/dialogue_understanding/__init__.py +0 -0
- rasa/dialogue_understanding/coexistence/__init__.py +0 -0
- rasa/dialogue_understanding/coexistence/constants.py +4 -0
- rasa/dialogue_understanding/coexistence/intent_based_router.py +189 -0
- rasa/dialogue_understanding/coexistence/llm_based_router.py +261 -0
- rasa/dialogue_understanding/coexistence/router_template.jinja2 +12 -0
- rasa/dialogue_understanding/commands/__init__.py +45 -0
- rasa/dialogue_understanding/commands/can_not_handle_command.py +61 -0
- rasa/dialogue_understanding/commands/cancel_flow_command.py +116 -0
- rasa/dialogue_understanding/commands/chit_chat_answer_command.py +48 -0
- rasa/dialogue_understanding/commands/clarify_command.py +77 -0
- rasa/dialogue_understanding/commands/command.py +85 -0
- rasa/dialogue_understanding/commands/correct_slots_command.py +288 -0
- rasa/dialogue_understanding/commands/error_command.py +67 -0
- rasa/dialogue_understanding/commands/free_form_answer_command.py +9 -0
- rasa/dialogue_understanding/commands/handle_code_change_command.py +64 -0
- rasa/dialogue_understanding/commands/human_handoff_command.py +57 -0
- rasa/dialogue_understanding/commands/knowledge_answer_command.py +48 -0
- rasa/dialogue_understanding/commands/noop_command.py +45 -0
- rasa/dialogue_understanding/commands/set_slot_command.py +125 -0
- rasa/dialogue_understanding/commands/skip_question_command.py +66 -0
- rasa/dialogue_understanding/commands/start_flow_command.py +98 -0
- rasa/dialogue_understanding/generator/__init__.py +6 -0
- rasa/dialogue_understanding/generator/command_generator.py +257 -0
- rasa/dialogue_understanding/generator/command_prompt_template.jinja2 +57 -0
- rasa/dialogue_understanding/generator/flow_document_template.jinja2 +4 -0
- rasa/dialogue_understanding/generator/flow_retrieval.py +410 -0
- rasa/dialogue_understanding/generator/llm_command_generator.py +637 -0
- rasa/dialogue_understanding/generator/nlu_command_adapter.py +157 -0
- rasa/dialogue_understanding/patterns/__init__.py +0 -0
- rasa/dialogue_understanding/patterns/cancel.py +111 -0
- rasa/dialogue_understanding/patterns/cannot_handle.py +43 -0
- rasa/dialogue_understanding/patterns/chitchat.py +37 -0
- rasa/dialogue_understanding/patterns/clarify.py +97 -0
- rasa/dialogue_understanding/patterns/code_change.py +41 -0
- rasa/dialogue_understanding/patterns/collect_information.py +90 -0
- rasa/dialogue_understanding/patterns/completed.py +40 -0
- rasa/dialogue_understanding/patterns/continue_interrupted.py +42 -0
- rasa/dialogue_understanding/patterns/correction.py +278 -0
- rasa/dialogue_understanding/patterns/default_flows_for_patterns.yml +243 -0
- rasa/dialogue_understanding/patterns/human_handoff.py +37 -0
- rasa/dialogue_understanding/patterns/internal_error.py +47 -0
- rasa/dialogue_understanding/patterns/search.py +37 -0
- rasa/dialogue_understanding/patterns/skip_question.py +38 -0
- rasa/dialogue_understanding/processor/__init__.py +0 -0
- rasa/dialogue_understanding/processor/command_processor.py +578 -0
- rasa/dialogue_understanding/processor/command_processor_component.py +39 -0
- rasa/dialogue_understanding/stack/__init__.py +0 -0
- rasa/dialogue_understanding/stack/dialogue_stack.py +178 -0
- rasa/dialogue_understanding/stack/frames/__init__.py +19 -0
- rasa/dialogue_understanding/stack/frames/chit_chat_frame.py +27 -0
- rasa/dialogue_understanding/stack/frames/dialogue_stack_frame.py +137 -0
- rasa/dialogue_understanding/stack/frames/flow_stack_frame.py +157 -0
- rasa/dialogue_understanding/stack/frames/pattern_frame.py +10 -0
- rasa/dialogue_understanding/stack/frames/search_frame.py +27 -0
- rasa/dialogue_understanding/stack/utils.py +211 -0
- rasa/e2e_test/__init__.py +0 -0
- rasa/e2e_test/constants.py +10 -0
- rasa/e2e_test/e2e_test_case.py +322 -0
- rasa/e2e_test/e2e_test_result.py +34 -0
- rasa/e2e_test/e2e_test_runner.py +659 -0
- rasa/e2e_test/e2e_test_schema.yml +67 -0
- rasa/engine/__init__.py +0 -0
- rasa/engine/caching.py +464 -0
- rasa/engine/constants.py +17 -0
- rasa/engine/exceptions.py +14 -0
- rasa/engine/graph.py +625 -0
- rasa/engine/loader.py +36 -0
- rasa/engine/recipes/__init__.py +0 -0
- rasa/engine/recipes/config_files/default_config.yml +44 -0
- rasa/engine/recipes/default_components.py +99 -0
- rasa/engine/recipes/default_recipe.py +1252 -0
- rasa/engine/recipes/graph_recipe.py +79 -0
- rasa/engine/recipes/recipe.py +93 -0
- rasa/engine/runner/__init__.py +0 -0
- rasa/engine/runner/dask.py +256 -0
- rasa/engine/runner/interface.py +49 -0
- rasa/engine/storage/__init__.py +0 -0
- rasa/engine/storage/local_model_storage.py +248 -0
- rasa/engine/storage/resource.py +110 -0
- rasa/engine/storage/storage.py +203 -0
- rasa/engine/training/__init__.py +0 -0
- rasa/engine/training/components.py +176 -0
- rasa/engine/training/fingerprinting.py +64 -0
- rasa/engine/training/graph_trainer.py +256 -0
- rasa/engine/training/hooks.py +164 -0
- rasa/engine/validation.py +839 -0
- rasa/env.py +5 -0
- rasa/exceptions.py +69 -0
- rasa/graph_components/__init__.py +0 -0
- rasa/graph_components/converters/__init__.py +0 -0
- rasa/graph_components/converters/nlu_message_converter.py +48 -0
- rasa/graph_components/providers/__init__.py +0 -0
- rasa/graph_components/providers/domain_for_core_training_provider.py +87 -0
- rasa/graph_components/providers/domain_provider.py +71 -0
- rasa/graph_components/providers/flows_provider.py +74 -0
- rasa/graph_components/providers/forms_provider.py +44 -0
- rasa/graph_components/providers/nlu_training_data_provider.py +56 -0
- rasa/graph_components/providers/responses_provider.py +44 -0
- rasa/graph_components/providers/rule_only_provider.py +49 -0
- rasa/graph_components/providers/story_graph_provider.py +43 -0
- rasa/graph_components/providers/training_tracker_provider.py +55 -0
- rasa/graph_components/validators/__init__.py +0 -0
- rasa/graph_components/validators/default_recipe_validator.py +552 -0
- rasa/graph_components/validators/finetuning_validator.py +302 -0
- rasa/hooks.py +113 -0
- rasa/jupyter.py +63 -0
- rasa/keys +1 -0
- rasa/markers/__init__.py +0 -0
- rasa/markers/marker.py +269 -0
- rasa/markers/marker_base.py +828 -0
- rasa/markers/upload.py +74 -0
- rasa/markers/validate.py +21 -0
- rasa/model.py +118 -0
- rasa/model_testing.py +457 -0
- rasa/model_training.py +535 -0
- rasa/nlu/__init__.py +7 -0
- rasa/nlu/classifiers/__init__.py +3 -0
- rasa/nlu/classifiers/classifier.py +5 -0
- rasa/nlu/classifiers/diet_classifier.py +1874 -0
- rasa/nlu/classifiers/fallback_classifier.py +192 -0
- rasa/nlu/classifiers/keyword_intent_classifier.py +188 -0
- rasa/nlu/classifiers/llm_intent_classifier.py +519 -0
- rasa/nlu/classifiers/logistic_regression_classifier.py +240 -0
- rasa/nlu/classifiers/mitie_intent_classifier.py +156 -0
- rasa/nlu/classifiers/regex_message_handler.py +56 -0
- rasa/nlu/classifiers/sklearn_intent_classifier.py +309 -0
- rasa/nlu/constants.py +77 -0
- rasa/nlu/convert.py +40 -0
- rasa/nlu/emulators/__init__.py +0 -0
- rasa/nlu/emulators/dialogflow.py +55 -0
- rasa/nlu/emulators/emulator.py +49 -0
- rasa/nlu/emulators/luis.py +86 -0
- rasa/nlu/emulators/no_emulator.py +10 -0
- rasa/nlu/emulators/wit.py +56 -0
- rasa/nlu/extractors/__init__.py +0 -0
- rasa/nlu/extractors/crf_entity_extractor.py +672 -0
- rasa/nlu/extractors/duckling_entity_extractor.py +206 -0
- rasa/nlu/extractors/entity_synonyms.py +178 -0
- rasa/nlu/extractors/extractor.py +470 -0
- rasa/nlu/extractors/mitie_entity_extractor.py +293 -0
- rasa/nlu/extractors/regex_entity_extractor.py +220 -0
- rasa/nlu/extractors/spacy_entity_extractor.py +95 -0
- rasa/nlu/featurizers/__init__.py +0 -0
- rasa/nlu/featurizers/dense_featurizer/__init__.py +0 -0
- rasa/nlu/featurizers/dense_featurizer/convert_featurizer.py +449 -0
- rasa/nlu/featurizers/dense_featurizer/dense_featurizer.py +57 -0
- rasa/nlu/featurizers/dense_featurizer/lm_featurizer.py +772 -0
- rasa/nlu/featurizers/dense_featurizer/mitie_featurizer.py +170 -0
- rasa/nlu/featurizers/dense_featurizer/spacy_featurizer.py +132 -0
- rasa/nlu/featurizers/featurizer.py +89 -0
- rasa/nlu/featurizers/sparse_featurizer/__init__.py +0 -0
- rasa/nlu/featurizers/sparse_featurizer/count_vectors_featurizer.py +840 -0
- rasa/nlu/featurizers/sparse_featurizer/lexical_syntactic_featurizer.py +539 -0
- rasa/nlu/featurizers/sparse_featurizer/regex_featurizer.py +269 -0
- rasa/nlu/featurizers/sparse_featurizer/sparse_featurizer.py +9 -0
- rasa/nlu/model.py +24 -0
- rasa/nlu/persistor.py +240 -0
- rasa/nlu/run.py +27 -0
- rasa/nlu/selectors/__init__.py +0 -0
- rasa/nlu/selectors/response_selector.py +990 -0
- rasa/nlu/test.py +1943 -0
- rasa/nlu/tokenizers/__init__.py +0 -0
- rasa/nlu/tokenizers/jieba_tokenizer.py +148 -0
- rasa/nlu/tokenizers/mitie_tokenizer.py +75 -0
- rasa/nlu/tokenizers/spacy_tokenizer.py +72 -0
- rasa/nlu/tokenizers/tokenizer.py +239 -0
- rasa/nlu/tokenizers/whitespace_tokenizer.py +106 -0
- rasa/nlu/utils/__init__.py +35 -0
- rasa/nlu/utils/bilou_utils.py +462 -0
- rasa/nlu/utils/hugging_face/__init__.py +0 -0
- rasa/nlu/utils/hugging_face/registry.py +108 -0
- rasa/nlu/utils/hugging_face/transformers_pre_post_processors.py +311 -0
- rasa/nlu/utils/mitie_utils.py +113 -0
- rasa/nlu/utils/pattern_utils.py +168 -0
- rasa/nlu/utils/spacy_utils.py +312 -0
- rasa/plugin.py +90 -0
- rasa/server.py +1536 -0
- rasa/shared/__init__.py +0 -0
- rasa/shared/constants.py +181 -0
- rasa/shared/core/__init__.py +0 -0
- rasa/shared/core/constants.py +168 -0
- rasa/shared/core/conversation.py +46 -0
- rasa/shared/core/domain.py +2106 -0
- rasa/shared/core/events.py +2507 -0
- rasa/shared/core/flows/__init__.py +7 -0
- rasa/shared/core/flows/flow.py +353 -0
- rasa/shared/core/flows/flow_step.py +146 -0
- rasa/shared/core/flows/flow_step_links.py +319 -0
- rasa/shared/core/flows/flow_step_sequence.py +70 -0
- rasa/shared/core/flows/flows_list.py +211 -0
- rasa/shared/core/flows/flows_yaml_schema.json +217 -0
- rasa/shared/core/flows/nlu_trigger.py +117 -0
- rasa/shared/core/flows/steps/__init__.py +24 -0
- rasa/shared/core/flows/steps/action.py +51 -0
- rasa/shared/core/flows/steps/call.py +64 -0
- rasa/shared/core/flows/steps/collect.py +112 -0
- rasa/shared/core/flows/steps/constants.py +5 -0
- rasa/shared/core/flows/steps/continuation.py +36 -0
- rasa/shared/core/flows/steps/end.py +22 -0
- rasa/shared/core/flows/steps/internal.py +44 -0
- rasa/shared/core/flows/steps/link.py +51 -0
- rasa/shared/core/flows/steps/no_operation.py +48 -0
- rasa/shared/core/flows/steps/set_slots.py +50 -0
- rasa/shared/core/flows/steps/start.py +30 -0
- rasa/shared/core/flows/validation.py +527 -0
- rasa/shared/core/flows/yaml_flows_io.py +278 -0
- rasa/shared/core/generator.py +907 -0
- rasa/shared/core/slot_mappings.py +235 -0
- rasa/shared/core/slots.py +647 -0
- rasa/shared/core/trackers.py +1159 -0
- rasa/shared/core/training_data/__init__.py +0 -0
- rasa/shared/core/training_data/loading.py +90 -0
- rasa/shared/core/training_data/story_reader/__init__.py +0 -0
- rasa/shared/core/training_data/story_reader/story_reader.py +129 -0
- rasa/shared/core/training_data/story_reader/story_step_builder.py +168 -0
- rasa/shared/core/training_data/story_reader/yaml_story_reader.py +888 -0
- rasa/shared/core/training_data/story_writer/__init__.py +0 -0
- rasa/shared/core/training_data/story_writer/story_writer.py +76 -0
- rasa/shared/core/training_data/story_writer/yaml_story_writer.py +442 -0
- rasa/shared/core/training_data/structures.py +838 -0
- rasa/shared/core/training_data/visualization.html +146 -0
- rasa/shared/core/training_data/visualization.py +603 -0
- rasa/shared/data.py +192 -0
- rasa/shared/engine/__init__.py +0 -0
- rasa/shared/engine/caching.py +26 -0
- rasa/shared/exceptions.py +129 -0
- rasa/shared/importers/__init__.py +0 -0
- rasa/shared/importers/importer.py +705 -0
- rasa/shared/importers/multi_project.py +203 -0
- rasa/shared/importers/rasa.py +100 -0
- rasa/shared/importers/utils.py +34 -0
- rasa/shared/nlu/__init__.py +0 -0
- rasa/shared/nlu/constants.py +45 -0
- rasa/shared/nlu/interpreter.py +10 -0
- rasa/shared/nlu/training_data/__init__.py +0 -0
- rasa/shared/nlu/training_data/entities_parser.py +209 -0
- rasa/shared/nlu/training_data/features.py +374 -0
- rasa/shared/nlu/training_data/formats/__init__.py +10 -0
- rasa/shared/nlu/training_data/formats/dialogflow.py +162 -0
- rasa/shared/nlu/training_data/formats/luis.py +87 -0
- rasa/shared/nlu/training_data/formats/rasa.py +135 -0
- rasa/shared/nlu/training_data/formats/rasa_yaml.py +605 -0
- rasa/shared/nlu/training_data/formats/readerwriter.py +245 -0
- rasa/shared/nlu/training_data/formats/wit.py +52 -0
- rasa/shared/nlu/training_data/loading.py +137 -0
- rasa/shared/nlu/training_data/lookup_tables_parser.py +30 -0
- rasa/shared/nlu/training_data/message.py +477 -0
- rasa/shared/nlu/training_data/schemas/__init__.py +0 -0
- rasa/shared/nlu/training_data/schemas/data_schema.py +85 -0
- rasa/shared/nlu/training_data/schemas/nlu.yml +53 -0
- rasa/shared/nlu/training_data/schemas/responses.yml +70 -0
- rasa/shared/nlu/training_data/synonyms_parser.py +42 -0
- rasa/shared/nlu/training_data/training_data.py +732 -0
- rasa/shared/nlu/training_data/util.py +223 -0
- rasa/shared/providers/__init__.py +0 -0
- rasa/shared/providers/openai/__init__.py +0 -0
- rasa/shared/providers/openai/clients.py +43 -0
- rasa/shared/providers/openai/session_handler.py +110 -0
- rasa/shared/utils/__init__.py +0 -0
- rasa/shared/utils/cli.py +72 -0
- rasa/shared/utils/common.py +308 -0
- rasa/shared/utils/constants.py +1 -0
- rasa/shared/utils/io.py +403 -0
- rasa/shared/utils/llm.py +405 -0
- rasa/shared/utils/pykwalify_extensions.py +26 -0
- rasa/shared/utils/schemas/__init__.py +0 -0
- rasa/shared/utils/schemas/config.yml +2 -0
- rasa/shared/utils/schemas/domain.yml +142 -0
- rasa/shared/utils/schemas/events.py +212 -0
- rasa/shared/utils/schemas/model_config.yml +46 -0
- rasa/shared/utils/schemas/stories.yml +173 -0
- rasa/shared/utils/yaml.py +777 -0
- rasa/studio/__init__.py +0 -0
- rasa/studio/auth.py +252 -0
- rasa/studio/config.py +127 -0
- rasa/studio/constants.py +16 -0
- rasa/studio/data_handler.py +352 -0
- rasa/studio/download.py +350 -0
- rasa/studio/train.py +136 -0
- rasa/studio/upload.py +408 -0
- rasa/telemetry.py +1583 -0
- rasa/tracing/__init__.py +0 -0
- rasa/tracing/config.py +338 -0
- rasa/tracing/constants.py +38 -0
- rasa/tracing/instrumentation/__init__.py +0 -0
- rasa/tracing/instrumentation/attribute_extractors.py +663 -0
- rasa/tracing/instrumentation/instrumentation.py +939 -0
- rasa/tracing/instrumentation/intentless_policy_instrumentation.py +142 -0
- rasa/tracing/instrumentation/metrics.py +206 -0
- rasa/tracing/metric_instrument_provider.py +125 -0
- rasa/utils/__init__.py +0 -0
- rasa/utils/beta.py +83 -0
- rasa/utils/cli.py +27 -0
- rasa/utils/common.py +635 -0
- rasa/utils/converter.py +53 -0
- rasa/utils/endpoints.py +303 -0
- rasa/utils/io.py +326 -0
- rasa/utils/licensing.py +319 -0
- rasa/utils/log_utils.py +174 -0
- rasa/utils/mapper.py +210 -0
- rasa/utils/ml_utils.py +145 -0
- rasa/utils/plotting.py +362 -0
- rasa/utils/singleton.py +23 -0
- rasa/utils/tensorflow/__init__.py +0 -0
- rasa/utils/tensorflow/callback.py +112 -0
- rasa/utils/tensorflow/constants.py +116 -0
- rasa/utils/tensorflow/crf.py +492 -0
- rasa/utils/tensorflow/data_generator.py +440 -0
- rasa/utils/tensorflow/environment.py +161 -0
- rasa/utils/tensorflow/exceptions.py +5 -0
- rasa/utils/tensorflow/layers.py +1565 -0
- rasa/utils/tensorflow/layers_utils.py +113 -0
- rasa/utils/tensorflow/metrics.py +281 -0
- rasa/utils/tensorflow/model_data.py +991 -0
- rasa/utils/tensorflow/model_data_utils.py +500 -0
- rasa/utils/tensorflow/models.py +936 -0
- rasa/utils/tensorflow/rasa_layers.py +1094 -0
- rasa/utils/tensorflow/transformer.py +640 -0
- rasa/utils/tensorflow/types.py +6 -0
- rasa/utils/train_utils.py +572 -0
- rasa/utils/yaml.py +54 -0
- rasa/validator.py +1035 -0
- rasa/version.py +3 -0
- rasa_pro-3.8.16.dist-info/METADATA +528 -0
- rasa_pro-3.8.16.dist-info/NOTICE +5 -0
- rasa_pro-3.8.16.dist-info/RECORD +644 -0
- rasa_pro-3.8.16.dist-info/WHEEL +4 -0
- rasa_pro-3.8.16.dist-info/entry_points.txt +3 -0
|
@@ -0,0 +1,229 @@
|
|
|
1
|
+
import json
|
|
2
|
+
|
|
3
|
+
import logging
|
|
4
|
+
import requests
|
|
5
|
+
from requests import Response
|
|
6
|
+
from sanic import Blueprint, response
|
|
7
|
+
from sanic.request import Request
|
|
8
|
+
from typing import Text, Dict, Any, List, Callable, Awaitable, Optional
|
|
9
|
+
|
|
10
|
+
from rasa.core.channels.channel import UserMessage, OutputChannel, InputChannel
|
|
11
|
+
from sanic.response import HTTPResponse
|
|
12
|
+
|
|
13
|
+
logger = logging.getLogger(__name__)
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class MattermostBot(OutputChannel):
|
|
17
|
+
"""A Mattermost communication channel."""
|
|
18
|
+
|
|
19
|
+
@classmethod
|
|
20
|
+
def name(cls) -> Text:
|
|
21
|
+
return "mattermost"
|
|
22
|
+
|
|
23
|
+
@classmethod
|
|
24
|
+
def token_from_login(cls, url: Text, user: Text, password: Text) -> Optional[Text]:
|
|
25
|
+
"""Retrieve access token for mattermost user."""
|
|
26
|
+
data = {"login_id": user, "password": password}
|
|
27
|
+
r = requests.post(url + "/users/login", data=json.dumps(data))
|
|
28
|
+
if r.status_code == 200:
|
|
29
|
+
return r.headers["Token"]
|
|
30
|
+
else:
|
|
31
|
+
logger.error(f"Failed to login mattermost user {user}. Response: {r}")
|
|
32
|
+
return None
|
|
33
|
+
|
|
34
|
+
def __init__(
|
|
35
|
+
self, url: Text, token: Text, bot_channel: Text, webhook_url: Optional[Text]
|
|
36
|
+
) -> None:
|
|
37
|
+
self.url = url
|
|
38
|
+
self.token = token
|
|
39
|
+
self.bot_channel = bot_channel
|
|
40
|
+
self.webhook_url = webhook_url
|
|
41
|
+
|
|
42
|
+
super(MattermostBot, self).__init__()
|
|
43
|
+
|
|
44
|
+
def _post_message_to_channel(self, channel_id: Text, message: Text) -> Response:
|
|
45
|
+
return self._post_data_to_channel(
|
|
46
|
+
{"channel_id": channel_id, "message": message}
|
|
47
|
+
)
|
|
48
|
+
|
|
49
|
+
def _post_data_to_channel(self, data: Dict[Text, Any]) -> Response:
|
|
50
|
+
"""Send a message to a mattermost channel."""
|
|
51
|
+
headers = {"Authorization": "Bearer " + self.token}
|
|
52
|
+
r = requests.post(self.url + "/posts", headers=headers, data=json.dumps(data))
|
|
53
|
+
if not r.status_code == 200:
|
|
54
|
+
logger.error(
|
|
55
|
+
f"Failed to send message to mattermost channel "
|
|
56
|
+
f"{data.get('channel_id')}. Response: {r}"
|
|
57
|
+
)
|
|
58
|
+
return r
|
|
59
|
+
|
|
60
|
+
async def send_text_message(
|
|
61
|
+
self, recipient_id: Text, text: Text, **kwargs: Any
|
|
62
|
+
) -> None:
|
|
63
|
+
for message_part in text.strip().split("\n\n"):
|
|
64
|
+
self._post_message_to_channel(self.bot_channel, message_part)
|
|
65
|
+
|
|
66
|
+
async def send_custom_json(
|
|
67
|
+
self, recipient_id: Text, json_message: Dict[Text, Any], **kwargs: Any
|
|
68
|
+
) -> None:
|
|
69
|
+
json_message.setdefault("channel_id", self.bot_channel)
|
|
70
|
+
json_message.setdefault("message", "")
|
|
71
|
+
|
|
72
|
+
self._post_data_to_channel(json_message)
|
|
73
|
+
|
|
74
|
+
async def send_image_url(
|
|
75
|
+
self, recipient_id: Text, image: Text, **kwargs: Any
|
|
76
|
+
) -> None:
|
|
77
|
+
"""Sends an image."""
|
|
78
|
+
self._post_data_to_channel(
|
|
79
|
+
{
|
|
80
|
+
"channel_id": self.bot_channel,
|
|
81
|
+
"props": {"attachments": [{"image_url": image}]},
|
|
82
|
+
}
|
|
83
|
+
)
|
|
84
|
+
|
|
85
|
+
async def send_text_with_buttons(
|
|
86
|
+
self,
|
|
87
|
+
recipient_id: Text,
|
|
88
|
+
text: Text,
|
|
89
|
+
buttons: List[Dict[Text, Any]],
|
|
90
|
+
**kwargs: Any,
|
|
91
|
+
) -> None:
|
|
92
|
+
"""Sends buttons to the output."""
|
|
93
|
+
# buttons are a list of objects: [(option_name, payload)]
|
|
94
|
+
# See https://docs.mattermost.com/developer/interactive-messages.html#message-buttons # noqa: E501
|
|
95
|
+
|
|
96
|
+
actions = [
|
|
97
|
+
{
|
|
98
|
+
"name": button["title"],
|
|
99
|
+
"integration": {
|
|
100
|
+
"url": self.webhook_url,
|
|
101
|
+
"context": {"action": button["payload"]},
|
|
102
|
+
},
|
|
103
|
+
}
|
|
104
|
+
for button in buttons
|
|
105
|
+
]
|
|
106
|
+
|
|
107
|
+
props = {"attachments": [{"actions": actions}]}
|
|
108
|
+
|
|
109
|
+
self._post_data_to_channel(
|
|
110
|
+
{"channel_id": self.bot_channel, "message": text, "props": props}
|
|
111
|
+
)
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
class MattermostInput(InputChannel):
|
|
115
|
+
"""Mattermost input channel implemenation."""
|
|
116
|
+
|
|
117
|
+
@classmethod
|
|
118
|
+
def name(cls) -> Text:
|
|
119
|
+
return "mattermost"
|
|
120
|
+
|
|
121
|
+
@classmethod
|
|
122
|
+
def from_credentials(cls, credentials: Optional[Dict[Text, Any]]) -> InputChannel:
|
|
123
|
+
if credentials is None:
|
|
124
|
+
cls.raise_missing_credentials_exception()
|
|
125
|
+
|
|
126
|
+
token = credentials.get("token")
|
|
127
|
+
|
|
128
|
+
return cls(credentials.get("url"), token, credentials.get("webhook_url"))
|
|
129
|
+
|
|
130
|
+
def __init__(self, url: Text, token: Text, webhook_url: Text) -> None:
|
|
131
|
+
"""Create a Mattermost input channel.
|
|
132
|
+
Needs a couple of settings to properly authenticate and validate
|
|
133
|
+
messages.
|
|
134
|
+
|
|
135
|
+
Args:
|
|
136
|
+
url: Your Mattermost team url including /v4 example
|
|
137
|
+
https://mysite.example.com/api/v4
|
|
138
|
+
token: Your mattermost bot token
|
|
139
|
+
webhook_url: The mattermost callback url as specified
|
|
140
|
+
in the outgoing webhooks in mattermost example
|
|
141
|
+
https://mysite.example.com/webhooks/mattermost/webhook
|
|
142
|
+
"""
|
|
143
|
+
self.url = url
|
|
144
|
+
self.token = token
|
|
145
|
+
self.webhook_url = webhook_url
|
|
146
|
+
|
|
147
|
+
async def message_with_trigger_word(
|
|
148
|
+
self,
|
|
149
|
+
on_new_message: Callable[[UserMessage], Awaitable[None]],
|
|
150
|
+
output: Dict[Text, Any],
|
|
151
|
+
metadata: Optional[Dict],
|
|
152
|
+
) -> None:
|
|
153
|
+
# splitting to get rid of the @botmention
|
|
154
|
+
# trigger we are using for this
|
|
155
|
+
split_message = output["text"].split(" ", 1)
|
|
156
|
+
if len(split_message) >= 2:
|
|
157
|
+
message = split_message[1]
|
|
158
|
+
else:
|
|
159
|
+
message = output["text"]
|
|
160
|
+
|
|
161
|
+
await self._handle_message(
|
|
162
|
+
message, output["user_id"], output["channel_id"], metadata, on_new_message
|
|
163
|
+
)
|
|
164
|
+
|
|
165
|
+
async def action_from_button(
|
|
166
|
+
self,
|
|
167
|
+
on_new_message: Callable[[UserMessage], Awaitable[None]],
|
|
168
|
+
output: Dict[Text, Any],
|
|
169
|
+
metadata: Optional[Dict],
|
|
170
|
+
) -> None:
|
|
171
|
+
# get the action, the buttons triggers
|
|
172
|
+
action = output["context"]["action"]
|
|
173
|
+
|
|
174
|
+
await self._handle_message(
|
|
175
|
+
action, output["user_id"], output["channel_id"], metadata, on_new_message
|
|
176
|
+
)
|
|
177
|
+
|
|
178
|
+
async def _handle_message(
|
|
179
|
+
self,
|
|
180
|
+
message: Text,
|
|
181
|
+
sender_id: Text,
|
|
182
|
+
bot_channel: Text,
|
|
183
|
+
metadata: Optional[Dict],
|
|
184
|
+
on_new_message: Callable[[UserMessage], Awaitable[None]],
|
|
185
|
+
) -> None:
|
|
186
|
+
try:
|
|
187
|
+
out_channel = MattermostBot(
|
|
188
|
+
self.url, self.token, bot_channel, self.webhook_url
|
|
189
|
+
)
|
|
190
|
+
user_msg = UserMessage(
|
|
191
|
+
message,
|
|
192
|
+
out_channel,
|
|
193
|
+
sender_id,
|
|
194
|
+
input_channel=self.name(),
|
|
195
|
+
metadata=metadata,
|
|
196
|
+
)
|
|
197
|
+
await on_new_message(user_msg)
|
|
198
|
+
except Exception as e:
|
|
199
|
+
logger.error(f"Exception when trying to handle message.{e}")
|
|
200
|
+
logger.debug(e, exc_info=True)
|
|
201
|
+
|
|
202
|
+
def blueprint(
|
|
203
|
+
self, on_new_message: Callable[[UserMessage], Awaitable[None]]
|
|
204
|
+
) -> Blueprint:
|
|
205
|
+
mattermost_webhook = Blueprint("mattermost_webhook", __name__)
|
|
206
|
+
|
|
207
|
+
@mattermost_webhook.route("/", methods=["GET"])
|
|
208
|
+
async def health(_: Request) -> HTTPResponse:
|
|
209
|
+
return response.json({"status": "ok"})
|
|
210
|
+
|
|
211
|
+
@mattermost_webhook.route("/webhook", methods=["POST"])
|
|
212
|
+
async def webhook(request: Request) -> HTTPResponse:
|
|
213
|
+
output = request.json
|
|
214
|
+
|
|
215
|
+
if not output:
|
|
216
|
+
return response.text("")
|
|
217
|
+
|
|
218
|
+
metadata = self.get_metadata(request)
|
|
219
|
+
# handle normal message with trigger_word
|
|
220
|
+
if "trigger_word" in output:
|
|
221
|
+
await self.message_with_trigger_word(on_new_message, output, metadata)
|
|
222
|
+
|
|
223
|
+
# handle context actions from buttons
|
|
224
|
+
elif "context" in output:
|
|
225
|
+
await self.action_from_button(on_new_message, output, metadata)
|
|
226
|
+
|
|
227
|
+
return response.text("success")
|
|
228
|
+
|
|
229
|
+
return mattermost_webhook
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
import json
|
|
2
|
+
from typing import Text, Optional, Dict, Any
|
|
3
|
+
|
|
4
|
+
import aiohttp
|
|
5
|
+
import logging
|
|
6
|
+
from sanic.exceptions import SanicException
|
|
7
|
+
import jwt
|
|
8
|
+
import jwt.exceptions
|
|
9
|
+
|
|
10
|
+
import rasa.core.channels.channel
|
|
11
|
+
from rasa.core.channels.channel import InputChannel
|
|
12
|
+
from rasa.core.channels.rest import RestInput
|
|
13
|
+
from rasa.core.constants import DEFAULT_REQUEST_TIMEOUT
|
|
14
|
+
from sanic.request import Request
|
|
15
|
+
|
|
16
|
+
logger = logging.getLogger(__name__)
|
|
17
|
+
|
|
18
|
+
CONVERSATION_ID_KEY = "conversation_id"
|
|
19
|
+
JWT_USERNAME_KEY = "username"
|
|
20
|
+
INTERACTIVE_LEARNING_PERMISSION = "clientEvents:create"
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
class RasaChatInput(RestInput):
|
|
24
|
+
"""Chat input channel for Rasa Enterprise."""
|
|
25
|
+
|
|
26
|
+
@classmethod
|
|
27
|
+
def name(cls) -> Text:
|
|
28
|
+
"""Name of the channel."""
|
|
29
|
+
return "rasa"
|
|
30
|
+
|
|
31
|
+
@classmethod
|
|
32
|
+
def from_credentials(cls, credentials: Optional[Dict[Text, Any]]) -> InputChannel:
|
|
33
|
+
if not credentials:
|
|
34
|
+
cls.raise_missing_credentials_exception()
|
|
35
|
+
|
|
36
|
+
return cls(credentials.get("url"))
|
|
37
|
+
|
|
38
|
+
def __init__(self, url: Optional[Text]) -> None:
|
|
39
|
+
"""Initialise the channel with attributes."""
|
|
40
|
+
self.base_url = url
|
|
41
|
+
self.jwt_key: Optional[Text] = None
|
|
42
|
+
self.jwt_algorithm = None
|
|
43
|
+
|
|
44
|
+
async def _fetch_public_key(self) -> None:
|
|
45
|
+
public_key_url = f"{self.base_url}/version"
|
|
46
|
+
async with aiohttp.ClientSession() as session:
|
|
47
|
+
async with session.get(
|
|
48
|
+
public_key_url, timeout=DEFAULT_REQUEST_TIMEOUT
|
|
49
|
+
) as resp:
|
|
50
|
+
status_code = resp.status
|
|
51
|
+
if status_code != 200:
|
|
52
|
+
logger.error(
|
|
53
|
+
"Failed to fetch JWT public key from URL '{}' with "
|
|
54
|
+
"status code {}: {}"
|
|
55
|
+
"".format(public_key_url, status_code, await resp.text())
|
|
56
|
+
)
|
|
57
|
+
return
|
|
58
|
+
rjs = await resp.json()
|
|
59
|
+
public_key_field = "keys"
|
|
60
|
+
if public_key_field in rjs:
|
|
61
|
+
self.jwt_key = rjs["keys"][0]["key"]
|
|
62
|
+
self.jwt_algorithm = rjs["keys"][0]["alg"]
|
|
63
|
+
logger.debug(
|
|
64
|
+
"Fetched JWT public key from URL '{}' for algorithm '{}':\n{}"
|
|
65
|
+
"".format(public_key_url, self.jwt_algorithm, self.jwt_key)
|
|
66
|
+
)
|
|
67
|
+
else:
|
|
68
|
+
logger.error(
|
|
69
|
+
"Retrieved json response from URL '{}' but could not find "
|
|
70
|
+
"'{}' field containing the JWT public key. Please make sure "
|
|
71
|
+
"you use an up-to-date version of Rasa Enterprise (>= 0.20.2). "
|
|
72
|
+
"Response was: {}"
|
|
73
|
+
"".format(public_key_url, public_key_field, json.dumps(rjs))
|
|
74
|
+
)
|
|
75
|
+
|
|
76
|
+
async def _decode_bearer_token(self, bearer_token: Text) -> Optional[Dict]:
|
|
77
|
+
if self.jwt_key is None:
|
|
78
|
+
await self._fetch_public_key()
|
|
79
|
+
|
|
80
|
+
try:
|
|
81
|
+
return rasa.core.channels.channel.decode_jwt(
|
|
82
|
+
bearer_token, self.jwt_key, self.jwt_algorithm
|
|
83
|
+
)
|
|
84
|
+
except jwt.InvalidSignatureError:
|
|
85
|
+
logger.error("JWT public key invalid, fetching new one.")
|
|
86
|
+
await self._fetch_public_key()
|
|
87
|
+
return rasa.core.channels.channel.decode_jwt(
|
|
88
|
+
bearer_token, self.jwt_key, self.jwt_algorithm
|
|
89
|
+
)
|
|
90
|
+
|
|
91
|
+
async def _extract_sender(self, req: Request) -> Optional[Text]:
|
|
92
|
+
"""Fetch user from the Rasa Enterprise Admin API."""
|
|
93
|
+
jwt_payload = None
|
|
94
|
+
if req.headers.get("Authorization"):
|
|
95
|
+
jwt_payload = await self._decode_bearer_token(req.headers["Authorization"])
|
|
96
|
+
|
|
97
|
+
if not jwt_payload:
|
|
98
|
+
jwt_payload = await self._decode_bearer_token(req.args.get("token"))
|
|
99
|
+
|
|
100
|
+
if not jwt_payload:
|
|
101
|
+
raise SanicException(status_code=401)
|
|
102
|
+
|
|
103
|
+
if CONVERSATION_ID_KEY in req.json:
|
|
104
|
+
if self._has_user_permission_to_send_messages_to_conversation(
|
|
105
|
+
jwt_payload, req.json
|
|
106
|
+
):
|
|
107
|
+
return req.json[CONVERSATION_ID_KEY]
|
|
108
|
+
else:
|
|
109
|
+
logger.error(
|
|
110
|
+
"User '{}' does not have permissions to send messages to "
|
|
111
|
+
"conversation '{}'.".format(
|
|
112
|
+
jwt_payload[JWT_USERNAME_KEY], req.json[CONVERSATION_ID_KEY]
|
|
113
|
+
)
|
|
114
|
+
)
|
|
115
|
+
raise SanicException(status_code=401)
|
|
116
|
+
|
|
117
|
+
return jwt_payload[JWT_USERNAME_KEY]
|
|
118
|
+
|
|
119
|
+
@staticmethod
|
|
120
|
+
def _has_user_permission_to_send_messages_to_conversation(
|
|
121
|
+
jwt_payload: Dict, message: Dict
|
|
122
|
+
) -> bool:
|
|
123
|
+
user_scopes = jwt_payload.get("scopes", [])
|
|
124
|
+
return INTERACTIVE_LEARNING_PERMISSION in user_scopes or message[
|
|
125
|
+
CONVERSATION_ID_KEY
|
|
126
|
+
] == jwt_payload.get(JWT_USERNAME_KEY)
|
|
@@ -0,0 +1,210 @@
|
|
|
1
|
+
import asyncio
|
|
2
|
+
import copy
|
|
3
|
+
import inspect
|
|
4
|
+
import json
|
|
5
|
+
import logging
|
|
6
|
+
import structlog
|
|
7
|
+
from asyncio import Queue, CancelledError
|
|
8
|
+
from sanic import Blueprint, response
|
|
9
|
+
from sanic.request import Request
|
|
10
|
+
from sanic.response import HTTPResponse, ResponseStream
|
|
11
|
+
from typing import Text, Dict, Any, Optional, Callable, Awaitable, NoReturn, Union
|
|
12
|
+
|
|
13
|
+
import rasa.utils.endpoints
|
|
14
|
+
from rasa.core.channels.channel import (
|
|
15
|
+
InputChannel,
|
|
16
|
+
CollectingOutputChannel,
|
|
17
|
+
UserMessage,
|
|
18
|
+
)
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
logger = logging.getLogger(__name__)
|
|
22
|
+
structlogger = structlog.get_logger()
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
class RestInput(InputChannel):
|
|
26
|
+
"""A custom http input channel.
|
|
27
|
+
|
|
28
|
+
This implementation is the basis for a custom implementation of a chat
|
|
29
|
+
frontend. You can customize this to send messages to Rasa and
|
|
30
|
+
retrieve responses from the assistant.
|
|
31
|
+
"""
|
|
32
|
+
|
|
33
|
+
@classmethod
|
|
34
|
+
def name(cls) -> Text:
|
|
35
|
+
return "rest"
|
|
36
|
+
|
|
37
|
+
@staticmethod
|
|
38
|
+
async def on_message_wrapper(
|
|
39
|
+
on_new_message: Callable[[UserMessage], Awaitable[Any]],
|
|
40
|
+
text: Text,
|
|
41
|
+
queue: Queue,
|
|
42
|
+
sender_id: Text,
|
|
43
|
+
input_channel: Text,
|
|
44
|
+
metadata: Optional[Dict[Text, Any]],
|
|
45
|
+
) -> None:
|
|
46
|
+
collector = QueueOutputChannel(queue)
|
|
47
|
+
|
|
48
|
+
message = UserMessage(
|
|
49
|
+
text, collector, sender_id, input_channel=input_channel, metadata=metadata
|
|
50
|
+
)
|
|
51
|
+
await on_new_message(message)
|
|
52
|
+
|
|
53
|
+
await queue.put("DONE")
|
|
54
|
+
|
|
55
|
+
async def _extract_sender(self, req: Request) -> Optional[Text]:
|
|
56
|
+
return req.json.get("sender", None)
|
|
57
|
+
|
|
58
|
+
# noinspection PyMethodMayBeStatic
|
|
59
|
+
def _extract_message(self, req: Request) -> Optional[Text]:
|
|
60
|
+
return req.json.get("message", None)
|
|
61
|
+
|
|
62
|
+
def _extract_input_channel(self, req: Request) -> Text:
|
|
63
|
+
return req.json.get("input_channel") or self.name()
|
|
64
|
+
|
|
65
|
+
def get_metadata(self, request: Request) -> Optional[Dict[Text, Any]]:
|
|
66
|
+
"""Extracts additional information from the incoming request.
|
|
67
|
+
|
|
68
|
+
Implementing this function is not required. However, it can be used to extract
|
|
69
|
+
metadata from the request. The return value is passed on to the
|
|
70
|
+
``UserMessage`` object and stored in the conversation tracker.
|
|
71
|
+
|
|
72
|
+
Args:
|
|
73
|
+
request: incoming request with the message of the user
|
|
74
|
+
|
|
75
|
+
Returns:
|
|
76
|
+
Metadata which was extracted from the request.
|
|
77
|
+
"""
|
|
78
|
+
return request.json.get("metadata", None)
|
|
79
|
+
|
|
80
|
+
def stream_response(
|
|
81
|
+
self,
|
|
82
|
+
on_new_message: Callable[[UserMessage], Awaitable[None]],
|
|
83
|
+
text: Text,
|
|
84
|
+
sender_id: Text,
|
|
85
|
+
input_channel: Text,
|
|
86
|
+
metadata: Optional[Dict[Text, Any]],
|
|
87
|
+
) -> Callable[[Any], Awaitable[None]]:
|
|
88
|
+
"""Streams response to the client.
|
|
89
|
+
|
|
90
|
+
If the stream option is enabled, this method will be called to
|
|
91
|
+
stream the response to the client
|
|
92
|
+
|
|
93
|
+
Args:
|
|
94
|
+
on_new_message: sanic event
|
|
95
|
+
text: message text
|
|
96
|
+
sender_id: message sender_id
|
|
97
|
+
input_channel: input channel name
|
|
98
|
+
metadata: optional metadata sent with the message
|
|
99
|
+
|
|
100
|
+
Returns:
|
|
101
|
+
Sanic stream
|
|
102
|
+
"""
|
|
103
|
+
|
|
104
|
+
async def stream(resp: Any) -> None:
|
|
105
|
+
q: Queue = Queue()
|
|
106
|
+
task = asyncio.ensure_future(
|
|
107
|
+
self.on_message_wrapper(
|
|
108
|
+
on_new_message, text, q, sender_id, input_channel, metadata
|
|
109
|
+
)
|
|
110
|
+
)
|
|
111
|
+
while True:
|
|
112
|
+
result = await q.get()
|
|
113
|
+
if result == "DONE":
|
|
114
|
+
break
|
|
115
|
+
else:
|
|
116
|
+
await resp.write(json.dumps(result) + "\n")
|
|
117
|
+
await task
|
|
118
|
+
|
|
119
|
+
return stream
|
|
120
|
+
|
|
121
|
+
def blueprint(
|
|
122
|
+
self, on_new_message: Callable[[UserMessage], Awaitable[None]]
|
|
123
|
+
) -> Blueprint:
|
|
124
|
+
"""Groups the collection of endpoints used by rest channel."""
|
|
125
|
+
module_type = inspect.getmodule(self)
|
|
126
|
+
if module_type is not None:
|
|
127
|
+
module_name = module_type.__name__
|
|
128
|
+
else:
|
|
129
|
+
module_name = None
|
|
130
|
+
|
|
131
|
+
custom_webhook = Blueprint(
|
|
132
|
+
"custom_webhook_{}".format(type(self).__name__),
|
|
133
|
+
module_name,
|
|
134
|
+
)
|
|
135
|
+
|
|
136
|
+
# noinspection PyUnusedLocal
|
|
137
|
+
@custom_webhook.route("/", methods=["GET"])
|
|
138
|
+
async def health(request: Request) -> HTTPResponse:
|
|
139
|
+
return response.json({"status": "ok"})
|
|
140
|
+
|
|
141
|
+
@custom_webhook.route("/webhook", methods=["POST"])
|
|
142
|
+
async def receive(request: Request) -> Union[ResponseStream, HTTPResponse]:
|
|
143
|
+
sender_id = await self._extract_sender(request)
|
|
144
|
+
text = self._extract_message(request)
|
|
145
|
+
should_use_stream = rasa.utils.endpoints.bool_arg(
|
|
146
|
+
request, "stream", default=False
|
|
147
|
+
)
|
|
148
|
+
input_channel = self._extract_input_channel(request)
|
|
149
|
+
metadata = self.get_metadata(request)
|
|
150
|
+
|
|
151
|
+
if should_use_stream:
|
|
152
|
+
return response.stream(
|
|
153
|
+
self.stream_response(
|
|
154
|
+
on_new_message, text, sender_id, input_channel, metadata
|
|
155
|
+
),
|
|
156
|
+
content_type="text/event-stream",
|
|
157
|
+
)
|
|
158
|
+
else:
|
|
159
|
+
collector = CollectingOutputChannel()
|
|
160
|
+
# noinspection PyBroadException
|
|
161
|
+
try:
|
|
162
|
+
await on_new_message(
|
|
163
|
+
UserMessage(
|
|
164
|
+
text,
|
|
165
|
+
collector,
|
|
166
|
+
sender_id,
|
|
167
|
+
input_channel=input_channel,
|
|
168
|
+
metadata=metadata,
|
|
169
|
+
headers=request.headers,
|
|
170
|
+
)
|
|
171
|
+
)
|
|
172
|
+
except CancelledError:
|
|
173
|
+
structlogger.error(
|
|
174
|
+
"rest.message.received.timeout", text=copy.deepcopy(text)
|
|
175
|
+
)
|
|
176
|
+
except Exception:
|
|
177
|
+
structlogger.exception(
|
|
178
|
+
"rest.message.received.failure", text=copy.deepcopy(text)
|
|
179
|
+
)
|
|
180
|
+
|
|
181
|
+
return response.json(collector.messages)
|
|
182
|
+
|
|
183
|
+
return custom_webhook
|
|
184
|
+
|
|
185
|
+
|
|
186
|
+
class QueueOutputChannel(CollectingOutputChannel):
|
|
187
|
+
"""Output channel that collects send messages in a list.
|
|
188
|
+
|
|
189
|
+
(doesn't send them anywhere, just collects them).
|
|
190
|
+
"""
|
|
191
|
+
|
|
192
|
+
# FIXME: this is breaking Liskov substitution principle
|
|
193
|
+
# and would require some user-facing refactoring to address
|
|
194
|
+
messages: Queue # type: ignore[assignment]
|
|
195
|
+
|
|
196
|
+
@classmethod
|
|
197
|
+
def name(cls) -> Text:
|
|
198
|
+
"""Name of QueueOutputChannel."""
|
|
199
|
+
return "queue"
|
|
200
|
+
|
|
201
|
+
# noinspection PyMissingConstructor
|
|
202
|
+
def __init__(self, message_queue: Optional[Queue] = None) -> None:
|
|
203
|
+
super().__init__()
|
|
204
|
+
self.messages = Queue() if not message_queue else message_queue
|
|
205
|
+
|
|
206
|
+
def latest_output(self) -> NoReturn:
|
|
207
|
+
raise NotImplementedError("A queue doesn't allow to peek at messages.")
|
|
208
|
+
|
|
209
|
+
async def _persist_message(self, message: Dict[Text, Any]) -> None:
|
|
210
|
+
await self.messages.put(message)
|