-
Notifications
You must be signed in to change notification settings - Fork 18
User guides #177
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
User guides #177
Changes from 3 commits
Commits
Show all changes
20 commits
Select commit
Hold shift + click to select a range
265abb9
user guides
pseusys 4ab79c2
basic guide
pseusys d327b04
section changed
pseusys a0e7e47
prints removed
pseusys af3c8fd
minor text fixes
RLKRo a889f20
labels reverted
pseusys 17558fe
Merge branch 'dev' into feat/user_guides
pseusys ddd1cbe
Merge branch 'feat/user_guides' of https://github.com/deeppavlov/dial…
pseusys 3e02379
Merge branch 'dev' into feat/user_guides
pseusys 9b5bc90
review revised
pseusys a0f0de1
fixes reverted
pseusys 6b63499
minor text fixes
RLKRo 9f913b9
some review comments taken into account
pseusys 363f442
Merge branch 'feat/user_guides' of https://github.com/deeppavlov/dial…
pseusys a8527d8
replace note with a shield badge
RLKRo 297f640
get_previous_node_name doc changes
RLKRo 3849316
chat bot specification fixed further
pseusys b84aa3f
Merge branch 'feat/user_guides' of https://github.com/deeppavlov/dial…
pseusys a6c04b5
more review comments fixed
pseusys c05582b
chat bot description updated
pseusys File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,10 @@ | ||
| User guides | ||
| ----------- | ||
|
|
||
| :doc:`Basic conceptions <./user_guides/basic_conceptions>` | ||
| ~~~~~~~~~~~~~~~~~ | ||
|
|
||
| In the ``basic conceptions`` tutorial the basics of DFF are described, | ||
| that include but are not limited to: dialog graph creation, specifying start and fallback nodes, | ||
| setting transitions and conditions, using ``Context`` object in order to receive information | ||
| about current script execution. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,288 @@ | ||
| Basic Concepts | ||
| -------------- | ||
|
|
||
| Introduction | ||
| ~~~~~~~~~~~~ | ||
|
|
||
| Dialog Flow Framework starts from creating conversational services, | ||
| defining a specialized dialog graph that dictates the behavior of the dialog service. | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| This dialog graph essentially represents the dialog script that guides the conversation | ||
| between the AI and the user. | ||
|
|
||
| The DFF leverages a specialized language known as a Domain-Specific Language (DSL) | ||
| to enable developers to quickly write and comprehend dialog graphs. | ||
| This DSL greatly simplifies the process of designing complex conversations and handling | ||
| various user inputs, making it easier to build sophisticated conversational systems. | ||
|
|
||
| DFF installation and requirements | ||
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| For this very basic tutorial we will need only the core dependencies of DFF. | ||
| They can be installed via the following command: | ||
|
|
||
| .. code-block:: shell | ||
|
|
||
| pip3 install dff | ||
|
|
||
| .. note:: | ||
|
|
||
| Any python version starting from Python 3.8 is supported by DFF, | ||
| however no tests for versions higher than 3.11 were executed. | ||
|
|
||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| Example conversational AI | ||
| ~~~~~~~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| Let us go through creation of a simple bot that would play (virtual) ping-pong game with user. | ||
| It will also greet user and handle exceptions. | ||
| First, we would define the AI in pseudo language: | ||
|
|
||
| .. code-block:: text | ||
|
|
||
| If user writes "Hello!": | ||
| Respond with "Hi! Let's play ping-pong!" | ||
|
|
||
| If user afterwards writes "Ping" or "ping" or "Ping!": | ||
| Respond with "Pong!" | ||
| Repeat this behaviour | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| If user afterwards writes something else: | ||
| Respond with "That was against the rules!" | ||
| Repeat from the beginning if user writes anything | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| Later in this tutorial we will create this AI using DFF, starting from the very basics | ||
| and then elaborating on more complicated topics. | ||
|
|
||
| Example AI graph | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| ~~~~~~~~~~~~~~~~ | ||
|
|
||
| Let's start from creating the very simple dialog agent implementation: | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| .. code-block:: python | ||
|
|
||
| from dff.pipeline import Pipeline | ||
| from dff.script import TRANSITIONS, RESPONSE, Message | ||
| import dff.script.conditions as cnd | ||
| from dff.utils.testing.common import run_interactive_mode | ||
|
|
||
| ping_pong_script = { | ||
| "ping_pong_flow": { | ||
| "start_node": { | ||
| RESPONSE: Message(), | ||
| TRANSITIONS: { | ||
| "greeting_node": cnd.exact_match(Message(text="Hello!")), | ||
| }, | ||
| }, | ||
| "greeting_node": { | ||
| RESPONSE: Message(text="Hi! Let's play ping-pong!"), | ||
| TRANSITIONS: { | ||
| "response_node": cnd.exact_match(Message(text="Ping!")), | ||
| }, | ||
| }, | ||
| "response_node": { | ||
| RESPONSE: Message(text="Pong!"), | ||
| TRANSITIONS: { | ||
| "response_node": cnd.exact_match(Message(text="Ping!")), | ||
| }, | ||
| }, | ||
| "fallback_node": { | ||
| RESPONSE: Message(text="That was against the rules!"), | ||
| TRANSITIONS: { | ||
| "greeting_node": cnd.true(), | ||
| }, | ||
| }, | ||
| }, | ||
| } | ||
|
|
||
| pipeline = Pipeline.from_script( | ||
| ping_pong_script, | ||
| start_label=("ping_pong_flow", "start_node"), | ||
| fallback_label=("ping_pong_flow", "fallback_node"), | ||
| ) | ||
|
|
||
| if __name__ == "__main__": | ||
| run_interactive_mode(pipeline) | ||
|
|
||
| .. warning:: | ||
|
|
||
| Current dialog agent implementation doesn't support different cases and/or marks in "Ping" | ||
| messages, it only supports exact "Ping!" message from user. | ||
|
|
||
| That's what the agent consists of: | ||
|
|
||
| * ``ping_pong_script`` in order to create a dialog agent, a dialog **script** is needed; | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| a script is a dictionary, where the keys are the names of the flows (that are "sub-dialogs", | ||
| used to separate the whole dialog into multiple sub-dialogs). | ||
|
|
||
| * ``ping_pong_flow`` is our behaviour flow; flow is a separated dialog, containing linked | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| conversation nodes and maybe some extra data, transitions, etc. | ||
|
|
||
| * ``start_node`` is the initial node, contains no response, only transfers user to an other node | ||
| according to the first message user sends. | ||
| It transfers user to ``greeting_node`` if user writes text message exactly equal to "Hello!". | ||
|
|
||
| * Each node contains "RESPONSE" and "TRANSITIONS" elements. | ||
|
|
||
| * ``RESPONSE`` value should be a ``Message`` object, that can contain text, images, | ||
| audios, attachments, etc. | ||
|
|
||
| * ``TRANSITIONS`` value should be a dict, containing node names and conditions, | ||
| that should be met in order to go to the node specified. | ||
| Here, we can see two different types of transitions: ``exact_match`` requires user message text to | ||
| match the provided text exactly, while ``true`` allowes unconditional transition. | ||
|
|
||
| * ``greeting_node`` is the node that will greet user and propose him a ping-pong game. | ||
| It transfers user to ``response_node`` if user writes text message exactly equal to "Ping!". | ||
|
|
||
| * ``response_node`` is the node that will play ping-pong game with the user. | ||
| It transfers user to ``response_node`` if user writes text message exactly equal to "Ping!". | ||
|
|
||
| * ``fallback_node`` is an "exception handling node"; user will be transferred here if in any node | ||
| no transition for the message given by user is found. | ||
| It transfers user to ``greeting_node`` no matter what user writes. | ||
|
|
||
| * ``pipeline`` is a special object that processes user requests according to provided script. | ||
| In order to create pipeline, the script should be provided and two two-string tuples: | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| the first specifies initial node flow and name and the second (optional) specifies fallback | ||
| node flow and name (if not provided it equals to the first one by default). | ||
|
|
||
| * ``run_interactive_mode`` is a function for dialog testing, it executes pipeline in a loop, | ||
| using CLI to accept user input and provide user with output. | ||
|
|
||
| .. note:: | ||
|
|
||
| See :doc:`tutorial on basic dialog structure <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.1_basics.html>`. | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| Advanced graph features | ||
| ~~~~~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| Right now the agent we have created is a very simple one and does not behaves **exactly** as we wanted | ||
| our bot to behave. Let's elaborate on that and see how can we improve our script: | ||
|
|
||
| .. code-block:: python | ||
|
|
||
| from dff.pipeline import Pipeline | ||
| from dff.script import TRANSITIONS, RESPONSE, Context, Message | ||
| import dff.script.conditions as cnd | ||
| import dff.script.labels as lbl | ||
| from dff.utils.testing.common import run_interactive_mode | ||
|
|
||
| def get_previous_node_name(ctx: Context) -> str: | ||
| last_label = list(ctx.labels)[-2] if len(ctx.labels) >= 2 else None | ||
| return ctx.labels[last_label][1] if last_label is not None else "start_node" | ||
pseusys marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
|
||
| def ping_pong_response(ctx: Context, _: Pipeline, *args, **kwargs) -> Message: | ||
| if get_previous_node_name(ctx) == "start_node": | ||
| return Message(text="Hi! Let's play ping-pong!") | ||
| else: | ||
| return Message(text="Pong!") | ||
|
|
||
| def fallback_response(ctx: Context, _: Pipeline, *args, **kwargs) -> Message: | ||
| if ctx.last_request is not None: | ||
| last_request = ctx.last_request.text | ||
| note = f"You should've written 'Ping', not '{last_request}'!" | ||
| else: | ||
| note = "You should've just written 'Ping'!" | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| if get_previous_node_name(ctx) == "start_node": | ||
| return Message(text="You should've started the dialog with 'Hello!'," | ||
| "anyway, let's play ping-pong!") | ||
| else: | ||
| return Message(text=f"That was against the rules! {note}") | ||
|
|
||
| ping_pong_script = { | ||
| "ping_pong_flow": { | ||
| "start_node": { | ||
| RESPONSE: Message(), | ||
| TRANSITIONS: { | ||
| lbl.forward(): cnd.exact_match(Message(text="Hello!")), | ||
| }, | ||
| }, | ||
| "ping_pong_node": { | ||
| RESPONSE: ping_pong_response, | ||
| TRANSITIONS: { | ||
| lbl.repeat(): cnd.regexp(r"^[P|p]ing!?$"), | ||
| }, | ||
| }, | ||
| "fallback_node": { | ||
| RESPONSE: fallback_response, | ||
| TRANSITIONS: { | ||
| lbl.backward(): cnd.regexp(r"^[P|p]ing!?$"), | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| }, | ||
| }, | ||
| }, | ||
| } | ||
|
|
||
| pipeline = Pipeline.from_script( | ||
| ping_pong_script, | ||
| start_label=("ping_pong_flow", "start_node"), | ||
| fallback_label=("ping_pong_flow", "fallback_node"), | ||
| ) | ||
|
|
||
| if __name__ == "__main__": | ||
| run_interactive_mode(pipeline) | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
|
|
||
| That's what we changed: | ||
|
|
||
| * ``greeting_node`` and ``response_node`` were merged, the resulting ``ping_pong_node`` has a | ||
pseusys marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| callback response, it proposes user to play ping-pong if the previous node was ``start_node`` and | ||
| plays ping-pong otherwise. | ||
|
|
||
| * ``fallback_node`` has a callback response as well, it prints different mesasages according to the | ||
| previous node, that messages can also include user inputs. | ||
|
|
||
| .. note:: | ||
|
|
||
| See :doc:`tutorial on response functions <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.3_responses.html>`. | ||
|
|
||
| * A special function ``get_previous_node_name`` was written to determine the value of the previous | ||
| visited node. It utilizes ``labels`` attribute of ``Context`` object. | ||
|
|
||
| .. note:: | ||
|
|
||
| See :doc:`documentation of Context object <https://deeppavlov.github.io/dialog_flow_framework/apiref/dff.script.core.context.html>`. | ||
|
|
||
| * Transitions were changed: transitions to next, previous and current node were replaced with special | ||
| standard transitions. | ||
|
|
||
| .. note:: | ||
|
|
||
| See :doc:`tutorial on transitions <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.4_transitions.html>`. | ||
|
|
||
| * Conditions were changed: now regular expressions are used to check user text input value. | ||
|
|
||
| .. note:: | ||
|
|
||
| See :doc:`tutorial on conditions <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.2_conditions.html>`. | ||
|
|
||
| Further exploration | ||
| ~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| There are still come capabilities of Dialog Flow Framework that remain uncovered by this tutorial. | ||
| For example: | ||
|
|
||
| * You can use ``GLOBAL`` transitions that will be available from every node in your script. | ||
| See :doc:`tutorial on global transitions <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.5_global_transitions.html>`. | ||
|
|
||
| * You can serialize context (available on every transition and response) | ||
RLKRo marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| to json or dictionary in order to debug it or extract some values. | ||
| See :doc:`tutorial on context serialization <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.6_context_serialization.html>`. | ||
|
|
||
| * You can alter user input and modify generated responses. | ||
| User input can be altered with ``PRE_RESPONSE_PROCESSING`` and will happen **before** response generation. | ||
| See :doc:`tutorial on pre-response processing <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.7_pre_response_processing.html>`. | ||
| Node response can be modified with ``PRE_TRANSITION_PROCESSING`` and will happen **after** response generation. | ||
| See :doc:`tutorial on pre-transition processing <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.9_pre_transitions_processing.html>`. | ||
|
|
||
| * Additional data ``MISC`` can be added to every node, flow and script itself. | ||
| The values in MISC will be available during one script execution only; they will be cleared on each new user input. | ||
RLKRo marked this conversation as resolved.
Outdated
Show resolved
Hide resolved
|
||
| See :doc:`tutorial on script MISC <https://deeppavlov.github.io/dialog_flow_framework/tutorials/tutorials.script.core.8_misc.html>`. | ||
|
|
||
| Conclusion | ||
| ~~~~~~~~~~ | ||
|
|
||
| In this tutorial, we explored the basics of Dialog Flow Framework (DFF) to build dynamic conversational services. | ||
| By using DFF's intuitive Domain-Specific Language (DSL) and well-structured dialog graphs, we created a simple interaction between user and AI. | ||
| We covered installation, understanding the DSL and building dialog graph. | ||
| However, this is just the beginning. DFF offers a world of possibilities in conversational AI. | ||
| With practice and exploration of advanced features, you can create human-like conversations and reach a wider audience by integrating with various platforms. | ||
| Now, go forth, unleash your creativity, and create captivating conversational services with DFF. | ||
| Happy building! | ||
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.