74 |
75 |
76 |
77 |
78 |
79 |
80 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/.buildpacks:
--------------------------------------------------------------------------------
1 | https://github.com/polettix/heroku-buildpack-perl-procfile.git
2 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/.env:
--------------------------------------------------------------------------------
1 | DATABASE_URL=postgres://postgres:${DB_PASS}@localhost:5432/bobbystable
2 | USERNAME=bobbystable
3 | PASSWORD=$(openssl rand -base64 10 | tr -dc 'a-zA-Z0-9')
4 | DEBUG=1
5 | BOBBYSTABLE=${PHONE_NUMBER}
6 | TOP_P=0.6
7 | TEMPERATURE=0.6
8 | ASSISTANT=${PHONE_NUMBER}
9 | SAVE_BLANK_CONVERSATIONS=1
10 | API_VERSION=api/relay/rest
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/Procfile:
--------------------------------------------------------------------------------
1 | web: perl ./app.pl daemon --listen "http://*:$PORT"
2 |
3 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/README.md:
--------------------------------------------------------------------------------
1 | # Bobbystable.ai
2 | https://Bobbystable.ai AI Reservation bot powered by [Signalwire](https://signalwire.com/?utm_source=bobbystable.ai)
3 |
4 | Live demo: Call `+1-754-432-6229`
5 |
6 | Welcome to Bobbystable.ai. Bobbystable.ai is a functional demo of a restaurant reservation system using Signalwire's APIs.
7 |
8 | In this repository, you will find the full prompt used, along with all the functions. The functions are written in Perl.
9 |
10 | In addition to what is included in this repository, you will also need a web server (NGINX), a database (PostgreSQL), Signalwire's APIs, and a registered/apporoved campaign for SMS.
11 |
12 | ### Docker Container
13 | #### To use Bobbystable.ai with a docker container please see [WireStarter](https://github.com/signalwire/WireStarter)
14 |
15 | -------------------
16 |
17 | The website is used to display the reservation details. This could be protected with a username and password, but it was left open to demonstrate the functionality.
18 |
19 | - `Date:` Reservation date.
20 | - `Time:` Reservation time.
21 | - `Party Size:` Number of guests.
22 | - `Guest Name:` Name of the guest.
23 | - `Guest Number:` Phone number of the guest.
24 |
25 | 
26 |
27 |
28 | ---------------------------
29 |
30 | This is a backend interface gated by a login user name and password.
31 |
32 | - `user:` The caller's interaction.
33 | - `Assistant:` The AI bot's interaction.
34 | - `function:` This shows that the function was executed either correctly or incorrectly.
35 | - `system:` This is like the assistant but on a higher level.
36 |
37 | 
38 |
39 |
40 | ----------------------------
41 |
42 | This is the text message sent that includes:
43 |
44 | - Reservation name.
45 | - Reservation date and time.
46 | - Instructions on how to update the reservation online with a unique link.
47 | - The option to STOP to help comply with sms regulation.
48 |
49 | 
50 |
51 |
52 | ---------------------
53 |
54 | ### SignalWire
55 |
56 | #### SignalWire’s AI Agent for Voice allows you to build and deploy your own digital employee. Powered by advanced natural language processing (NLP) capabilities, your digital employee will understand caller intent, retain context, and generally behave in a way that feels “human-like”. In fact, you may find that it behaves exactly like your best employee, elevating the customer experience through efficient, intelligent, and personalized interactions.
57 |
58 |
59 |
60 |
61 |
62 |
63 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/bobbystable.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Perl_Examples/BobbysTable.ai/assets/bobbystable.png
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/crintaspot.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Perl_Examples/BobbysTable.ai/assets/crintaspot.png
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/dinedash.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Perl_Examples/BobbysTable.ai/assets/dinedash.png
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/mealzoom.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Perl_Examples/BobbysTable.ai/assets/mealzoom.png
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/rapidfeast.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Perl_Examples/BobbysTable.ai/assets/rapidfeast.png
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/assets/style.css:
--------------------------------------------------------------------------------
1 | .inline-form {
2 | display: inline-block;
3 | margin-right: 10px;
4 | }
5 |
6 | .pi-container {
7 | position: fixed;
8 | bottom: 10px;
9 | right: 10px;
10 | text-align: right;
11 | }
12 |
13 | .pi-symbol, .pi-link {
14 | font-size: small;
15 | color: #808080;
16 | text-decoration: none;
17 | }
18 |
19 | .pi-link:hover {
20 | text-decoration: underline;
21 | }
22 |
23 | .center-table {
24 | margin-left: auto;
25 | margin-right: auto;
26 | }
27 |
28 | body {
29 | font-family: Tahoma, Arial, sans-serif;
30 | color: #ffffff;
31 | background-color: #222222;
32 | }
33 |
34 | left-col {
35 | width: 20%;
36 | }
37 |
38 | .right-col {
39 | width: 80%;
40 | }
41 |
42 | table {
43 | width: 90%;
44 | margin: 0 auto;
45 | border: none;
46 | border-spacing: 0px;
47 | margin-left: auto;
48 | margin-right: auto;
49 | border-collapse: collapse;
50 | }
51 |
52 | table th, table td {
53 | border: none;
54 | text-align: left;
55 | }
56 |
57 | table td {
58 | padding: 10px;
59 | min-width: 100px;
60 | }
61 |
62 | h1, a {
63 | color: #000000;
64 | }
65 |
66 | h2 {
67 | text-align: center;
68 | color: #ffffff;
69 | }
70 |
71 | a {
72 | text-decoration: none;
73 | color: #50D2E9; /* If there's a conflict, choose one color */
74 | }
75 |
76 | a:hover {
77 | color: #33CCFF;
78 | }
79 |
80 | button, .submit-button {
81 | font-size: 16px;
82 | color: #FFFFFF;
83 | background-color: #4CAF50;
84 | border: none;
85 | padding: 10px 20px;
86 | text-align: center;
87 | cursor: pointer;
88 | border-radius: 4px;
89 | }
90 |
91 | button, .edit-button {
92 | font-size: 16px;
93 | color: #FFFFFF;
94 | background-color: #4CAF50;
95 | border: none;
96 | padding: 10px 20px;
97 | text-align: center;
98 | cursor: pointer;
99 | border-radius: 4px;
100 | }
101 |
102 | button, .delete-button {
103 | font-size: 16px;
104 | color: #FFFFFF;
105 | background-color: #FF0000;
106 | border: none;
107 | padding: 10px 20px;
108 | text-align: center;
109 | cursor: pointer;
110 | border-radius: 4px;
111 | }
112 |
113 | button, .add-button {
114 | font-size: 16px;
115 | color: #FFFFFF;
116 | background-color: #4CAF50;
117 | border: none;
118 | padding: 10px 20px;
119 | text-align: center;
120 | cursor: pointer;
121 | border-radius: 4px;
122 | }
123 |
124 | button:hover, .submit-button:hover {
125 | background-color: #45a049;
126 | }
127 |
128 | header {
129 | background-color: #f2f2f2;
130 | padding: 10px;
131 | text-align: center;
132 | }
133 |
134 | header nav a {
135 | margin: 0 10px;
136 | text-decoration: none;
137 | color: #333;
138 | }
139 |
140 | .collapsible {
141 | cursor: pointer;
142 | text-align: center;
143 | width: auto;
144 | display: inline-block;
145 | }
146 |
147 | .content {
148 | display: none;
149 | overflow: hidden;
150 | background-color: #222222;
151 | margin: 0 auto;
152 | }
153 |
154 | .copy-button {
155 | text-align: center;
156 | width: auto;
157 | cursor: pointer;
158 | }
159 |
160 | .system {
161 | background-color: #872126;
162 | }
163 |
164 | .assistant {
165 | background-color: #364285;
166 | }
167 |
168 | .user {
169 | background-color: #236A1C;
170 | }
171 |
172 | .function {
173 | background-color: #CD00C4;
174 | }
175 |
176 | .center-table {
177 | margin-left: auto;
178 | margin-right: auto;
179 | border-collapse: collapse;
180 | }
181 |
182 | /* Optional: additional styling for the table */
183 | .center-table, .center-table th, .center-table td {
184 | border: 0px;
185 | }
186 |
187 | .center-table th, .center-table td {
188 | padding: 8px;
189 | text-align: left;
190 | }
191 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/bobbystable.sql:
--------------------------------------------------------------------------------
1 | INSERT INTO restaurants
2 | (name, open_time, close_time, days_open, capacity)
3 | VALUES
4 | ('Bobby''s Table', '09:00:00', '22:00:00', ARRAY['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday'], 50);
5 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/cpanfile:
--------------------------------------------------------------------------------
1 | requires 'File::Slurp', '9999.32';
2 | requires 'SignalWire::RestAPI', '1.5';
3 | requires 'SignalWire::ML', '1.20';
4 | requires 'Time::Piece', '1.3401';
5 | requires 'List::Util', '1.63';
6 | requires 'LWP::Protocol::https', '6.10';
7 | requires 'Plack', '1.0050';
8 | requires 'Data::Dumper', '2.174';
9 | requires 'LWP::UserAgent', '6.70';
10 | requires 'JSON::PP', '4.16';
11 | requires 'URL::Encode', '0.03';
12 | requires 'HTTP::Request::Common', '6.44';
13 | requires 'Env::C', '0.15';
14 | requires 'DBI', '1.643';
15 | requires 'DBD::Pg', '3.16.3';
16 | requires 'HTML::Template::Expr', '0.07';
17 | requires 'DateTime', '1.59';
18 | requires 'UUID', '0.28';
19 | requires 'MIME::Base64', '3.16';
20 | requires 'Twiggy', '0.1026';
21 |
22 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/post_prompt.md:
--------------------------------------------------------------------------------
1 | Summarize the conversation, including all the details.
2 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/prompt.md:
--------------------------------------------------------------------------------
1 | # Personality and Introduction
2 |
3 | You are a witty hostess and your name is Bobby. You work for bobby's table dot A eye. Greet the user with that information.
4 |
5 | # Your Skills, Knowledge, and Behavior
6 |
7 | # Address
8 | 327 Drop Table Lane
9 | Pompano Beach, FL 33060
10 |
11 | # Hours
12 | Open 2PM to 11PM, Monday through Saturday, Closed every Sunday.
13 | Same day reservations are allowed during business hours.
14 |
15 | # Check Availability
16 | Use function check_availability to check seat availability.
17 | If the time requested isn't available offer available times.
18 |
19 | # Create Reservation
20 | Use function create_reservation to create a reservation.
21 | Gather the user Reservation name, Reservation date, Reservation time and Reservation party size to Create a reservation.
22 |
23 | # Send Message
24 | Use function send_message to send a message.
25 |
26 | # Move Reservation
27 | Use the function move_reservation to find an existing reservation.
28 | Verify the reservation is the correct one.
29 | Then function move_reservation to move an existing reservation.
30 |
31 | # Lookup Reservation
32 | Use function lookup_reservation to find an existing reservation.
33 | You can only lookup a reservation by phone number.
34 | If you have difficulties understanding the number, you can ask the user to dial the number on their keypad.
35 | You can use the users phone number to look up a reservation, if none is found ask for the number the reservation is under.
36 |
37 | # Cancel Reservation
38 | Use the function lookup_reservation to find an existing reservation.
39 | Verify the reservation is the correct one.
40 | Then function cancel_reservation to cancel a reservation.
41 |
42 | # Conversation Flow
43 | These are the steps you need to follow during this conversation. Ensure you are strictly following the steps below in order.
44 |
45 | ## Step 1
46 | Ask how the user is today. Wait for the user to respond.
47 |
48 | ## Step 1.1
49 | Ask the user if they would like to create, move or cancel a reservation.
50 |
51 | ## Step 2
52 | If the user asks to create a reservation ask in sequence for:
53 |
54 | ## Step 2.1
55 | Ask for their name.
56 | ## Step 2.2
57 | Ask Party size. Can accomodate 16 or less.
58 | ## Step 2.3
59 | Ask Reservation date.
60 | ## Step 2.4
61 | Ask Reservation time.
62 | ## Step 2.5
63 | Ask if the number they are calling from is the same number they want to use for the reservation.
64 | ## Step 2.6
65 | Check for availability, if there is no availability offer other times then check those before proceeding.
66 | ## Step 2.7
67 | Create the reservation when the user agrees to the reservation date and time.
68 |
69 | ## Step 3
70 | Offer to send the user a message with the details of the reservation with reservation url link, messaging and data rates may apply. If user says yes then use the send_message function.
71 |
72 | ## Step 4
73 | If the user asks to update a reservation ask the user what the phone number is for the reservation, Repeat what the reservation name is to confirm with the user.
74 | ## Step 4.1
75 | Offer to send a message with the updated details.
76 |
77 | ## Step 5
78 | If the user asks to cancel a reservation ask the user why they want to cancel, Ask what the phone number is for the reservation. Repeat what the reservation name is to confirm with the user.
79 | ### Step 5.1
80 | Offer to send a message with the cancellation details.
81 | ### Step 5.2
82 | Repeat the reservation details to the user.
83 |
84 |
85 | ## Step 6
86 | When the user is ready to end the call, always say "Thank you for choosing bobby's table dot A I." then hangup.
87 |
--------------------------------------------------------------------------------
/server/Perl_Examples/BobbysTable.ai/template/conversation.tmpl:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Conversation Details
5 |
6 |
7 |
8 |
9 |
This Privacy Policy ("Policy") describes how [Your Company Name], a [Your Company's Legal Status] ("Company," "we," "us," or "our"), collects, uses, and protects the personal information you provide to us when using our AI Agent Calendar service (the "Service").
12 |
13 |
1. Information We Collect
14 |
1.1. User-Provided Information: We may collect personal information you provide when using the Service, including but not limited to your name, email address, and other contact information.
15 |
1.2. Usage Data: We may collect information about how you interact with the Service, including usage patterns, preferences, and activity logs.
16 |
17 |
2. How We Use Your Information
18 |
2.1. Service Operation: We use your information to provide and maintain the Service, enhance user experience, and respond to your requests.
19 |
2.2. Communication: We may use your contact information to communicate with you, send updates, and provide customer support.
20 |
21 |
3. Data Protection
22 |
3.1. Security: We implement reasonable security measures to protect your personal information. However, no method of transmission over the internet is entirely secure.
23 |
24 |
4. Sharing Your Information
25 |
4.1. Third-Party Services: We may share your information with third-party service providers that assist us in delivering the Service. These providers are contractually obligated to protect your data.
26 |
4.2. Legal Requirements: We may disclose your information to comply with legal obligations or in response to lawful requests.
27 |
28 |
5. Your Choices
29 |
5.1. Access and Control: You may access, update, or delete your personal information by contacting us.
30 |
31 |
6. Changes to This Policy
32 |
6.1. Updates: We may update this Policy periodically. Any changes will be posted on this page, and the revised Policy will be effective upon posting.
33 |
34 |
7. Contact Us
35 |
7.1. Contact: For questions or concerns regarding this Policy, please contact us at [Your Contact Information].
This Terms of Service Agreement (the "Agreement") is entered into between [Your Company Name], a [Your Company's Legal Status] ("Company," "we," "us," or "our"), and you, the user ("User," "you," or "your"). This Agreement governs your access to and use of the AI Agent Calendar service (the "Service").
12 |
13 |
1. Use of the Service
14 |
1.1. Eligibility: You must be at least 18 years old or have the necessary legal capacity in your jurisdiction to use the Service.
15 |
1.2. User Account: To access certain features of the Service, you may be required to create a user account. You are responsible for maintaining the confidentiality of your account credentials and for any activities that occur under your account.
16 |
1.3. Acceptable Use: You agree to use the Service in compliance with all applicable laws and regulations and in a manner that does not violate the rights of others or interfere with the operation of the Service.
17 |
18 |
2. Privacy
19 |
2.1. Data Collection: Our Privacy Policy (see below) explains how we collect, use, and protect your personal information. By using the Service, you consent to the collection and use of your data as described in the Privacy Policy.
20 |
21 |
3. Intellectual Property
22 |
3.1. Ownership: The Service, including all content, features, and functionality, is owned by the Company and protected by intellectual property laws. You may not reproduce, distribute, or modify any part of the Service without our express consent.
23 |
24 |
4. Limitation of Liability
25 |
4.1. Disclaimer: The Service is provided "as is" without warranties of any kind, whether express or implied. We do not guarantee the accuracy or availability of the Service.
26 |
4.2. Limitation of Liability: To the extent permitted by law, we shall not be liable for any direct, indirect, incidental, special, or consequential damages arising from your use of the Service.
27 |
28 |
5. Termination
29 |
5.1. Termination by Us: We reserve the right to terminate or suspend your access to the Service at our discretion, with or without notice, for any reason.
30 |
31 |
6. Governing Law
32 |
6.1. Jurisdiction: This Agreement is governed by and construed in accordance with the laws of [Your Jurisdiction], without regard to its conflict of law principles.
33 |
34 |
7. Contact Information
35 |
7.1. Contact: For questions or concerns regarding this Agreement, please contact us at [Your Contact Information].
36 |
37 |
38 |
39 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/Procfile:
--------------------------------------------------------------------------------
1 | web: python app.py
2 |
3 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/env.example:
--------------------------------------------------------------------------------
1 | HTTP_USERNAME=admin
2 | HTTP_PASSWORD=password
3 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/post_prompt.md:
--------------------------------------------------------------------------------
1 | ### **Post-Interaction Summary Instructions**
2 |
3 | After concluding each user interaction, please provide a concise summary of the call details. The summary should include:
4 |
5 | - **User's Request**: A brief description of what the user wanted to accomplish (e.g., create a new reservation, update an existing reservation).
6 | - **Information Collected**: Key details gathered from the user, such as name, party size, date, time, and confirmation of the phone number used.
7 | - **Actions Taken**: Any actions performed during the interaction, like creating, updating, moving, or canceling a reservation.
8 | - **Confirmation Provided**: Details of any confirmations given to the user regarding their reservation status.
9 |
10 | Ensure the summary accurately reflects the conversation and the services provided, while maintaining a friendly and professional tone.
11 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/requirements.txt:
--------------------------------------------------------------------------------
1 | Flask
2 | Flask_HTTPAuth
3 | python-dotenv
4 | signalwire_swaig
5 | gunicorn
6 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/runtime.txt:
--------------------------------------------------------------------------------
1 | python-3.11.10
2 |
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/static/img/bobbystable.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/signalwire/digital_employees/b3b8abc9b0c545f8363049f4ea69802938c15a2e/server/Python_Examples/bobbystable/static/img/bobbystable.png
--------------------------------------------------------------------------------
/server/Python_Examples/bobbystable/static/reservation.html:
--------------------------------------------------------------------------------
1 |
2 |
3 | Bobby's Table
4 |
5 |
6 |
7 |
8 |
9 |
10 |
45 |
46 |
47 |
48 |
52 |
53 |
--------------------------------------------------------------------------------
/server/README.md:
--------------------------------------------------------------------------------
1 |
2 |
--------------------------------------------------------------------------------
/server/tools/tap/README.md:
--------------------------------------------------------------------------------
1 | # Listening (tap) to RTP Audio Streams with Python and SWML
2 |
3 |
4 |
5 | ---
6 |
7 | **Table of Contents**
8 |
9 | - [Core Functionality](#core-functionality)
10 | - [Using tap](#using-tap)
11 | - [Using web tap](#using-web-tap)
12 | - [Utilizing the `tap` Method in SWML](#utilizing-the-tap-method-in-swml)
13 |
14 | ---
15 |
16 | The `tap` Python script is designed to listen to Real-time Transport Protocol (RTP) audio streams, decode PCMU (μ-law) audio, and play it using PyAudio, with support for multiple streams.
17 |
18 | ---
19 |
20 | ## Core Functionality
21 |
22 | The `tap` script handles the following tasks:
23 |
24 | - **RTP Packet Reception**:
25 | Listens for UDP-based RTP packets on a specified IP and port (e.g., `0.0.0.0:5004`).
26 |
27 | - **Audio Decoding**:
28 | Converts PCMU audio (payload type 0) to 16-bit PCM using a μ-law lookup table for playback.
29 |
30 | - **Multi-Stream Support**:
31 | Tracks multiple Synchronization Sources (SSRCs) and allows switching between them using arrow keys.
32 |
33 | - **Stream Cleanup**:
34 | Removes inactive SSRCs after a 2-second timeout.
35 |
36 | ---
37 |
38 | ## Using tap
39 |
40 | - **Run the Script**: Execute it in a Windows command prompt or terminal.
41 | - **Controls**:
42 | - **Left Arrow**: Switch to the previous active SSRC.
43 | - **Right Arrow**: Switch to the next active SSRC.
44 | - **'q'**: Exit the script.
45 | - **Requirements**: Ensure PyAudio is installed (`pip install pyaudio`) and your system has an audio output device.
46 |
47 | ---
48 |
49 | ## Using web tap
50 |
51 | - **Run the Script**: Execute it in a Windows command prompt or terminal.
52 | - **View Webpage**:
53 | Go to `http://ip:8080`, where `ip` is the address of the machine running the Python script. For example: `http://192.168.100.50:8080`.
54 | - **Start Listening**: Click to start receiving the incoming RTP stream.
55 | - **Listen/Listening**:
56 | If you have one or more than one stream, click "Listen." This will change the button to "Listening," and you will be able to hear the RTP stream through your web browser.
57 |
58 | 
59 |
60 | ---
61 |
62 | ## Utilizing the `tap` Method in SWML
63 |
64 | The `tap` method in SignalWire Markup Language (SWML) enables developers to stream call audio to an external destination via WebSocket or RTP. This functionality is essential for applications requiring real-time audio processing, such as call monitoring or recording.
65 |
66 | ### Key Parameters
67 |
68 | - **uri** (string, required): Specifies the destination for the audio stream. Supported formats include:
69 | - `rtp://IP:port`
70 | - `ws://example.com`
71 | - `wss://example.com`
72 |
73 | - **control_id** (string, optional): An identifier for the tap session, useful for managing or stopping the tap later. If not provided, a unique ID is auto-generated and stored in the `tap_control_id` variable.
74 |
75 | - **direction** (string, optional): Defines which part of the audio to tap:
76 | - `speak`: Audio sent from the party.
77 | - `listen`: Audio received by the party.
78 | - `both`: Both incoming and outgoing audio.
79 |
80 | Default is `speak`.
81 |
82 | - **codec** (string, optional): Specifies the audio codec, either `PCMU` or `PCMA`. Default is `PCMU`.
83 |
84 | - **rtp_ptime** (integer, optional): Applicable for RTP streams; sets the packetization time in milliseconds. Default is 20 ms.
85 |
86 | ### Example Usage
87 |
88 | Add the following to your SWML script to enable RTP tap:
89 |
90 | ```json
91 | {
92 | "version": "1.0.0",
93 | "sections": {
94 | "main": [
95 | {
96 | "tap": {
97 | "uri": "rtp://127.0.0.1:5004",
98 | "direction": "both"
99 | }
100 | }
101 | ]
102 | }
103 | }
104 | ```
105 |
106 | Note: Update the uri IP address to your public IP address.
107 |
--------------------------------------------------------------------------------
/server/tools/tap/SWML.json:
--------------------------------------------------------------------------------
1 | {
2 | "version": "1.0.0",
3 | "sections": {
4 | "main": [
5 | {
6 | "tap": {
7 | "uri": "rtp://127.0.0.1:5004",
8 | "direction": "both"
9 | }
10 | }
11 | }
12 | ]
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/serverless/Bartender/SWML.yaml:
--------------------------------------------------------------------------------
1 | sections:
2 | main:
3 | - answer: {}
4 | - record_call:
5 | format: "wav"
6 | stereo: "true"
7 | - ai:
8 | params:
9 | verbose_logs: "true"
10 | post_prompt_url: "optional.fake.tld"
11 | post_prompt:
12 | top_p: 0.6
13 | temperature: 0.6
14 | text: |
15 | Summarize the conversation and send the conversation as a message to the user in an anonymous json object.
16 |
17 | # Step 1
18 |
19 | hints:
20 | - "drinks"
21 | languages:
22 | - code: "en-US"
23 | voice: "alloy"
24 | name: "English"
25 | fillers:
26 | - "one moment"
27 | - "one moment please"
28 | engine: "openai"
29 | SWAIG:
30 | defaults: {}
31 | functions:
32 | - purpose: "use to send text messages to a user"
33 | argument:
34 | type: "object"
35 | properties:
36 | to:
37 | type: "string"
38 | description: "The user's number in e.164 format"
39 | message:
40 | description: "the message to send to the user"
41 | type: "string"
42 | data_map:
43 | expressions:
44 | - string: "${args.message}"
45 | output:
46 | response: "Message sent."
47 | action:
48 | - SWML:
49 | version: "1.0.0"
50 | sections:
51 | main:
52 | - send_sms:
53 | to_number: "${args.to}"
54 | region: "us"
55 | body: "${args.message}, ${chunks[0].text} ${chunks[0].document_id} Reply STOP to stop."
56 | from_number: "+15555555555"
57 | pattern: ".*"
58 | function: "send_message"
59 | - function: "get_vector_data"
60 | fillers:
61 | en-US:
62 | - "This is the get vector data function firing"
63 | data_map:
64 | webhooks:
65 | - method: "POST"
66 | url: "https://space_name.signalwire.com/api/datasphere/documents/search"
67 | headers:
68 | Content-Type: "application/json"
69 | Authorization: "Basic OGVhMjI0YzktM--USE--Project_ID:API_KEY--TO-BASE64-ENCODE--NkYjFh"
70 | params:
71 | query_string: "${args.user_question}"
72 | document_id: "694ced7b-b656-417e-bc86-ce22549b4562"
73 | count: 1
74 | output:
75 | response: " Use this information to answer the users query, only provide answers from this information and do not make up anything: ${chunks[0].text} and ${chunks[0].document_id}"
76 | action: []
77 | purpose: "The question the user will ask"
78 | argument:
79 | type: "object"
80 | properties:
81 | user_question:
82 | type: "string"
83 | description: "The question the user will ask. Use url encoding between words. for example: how%20are%20you"
84 | prompt:
85 | text: |
86 | You're an expert mixologist and work as a bartender. You have one function to send messages and You have a function get_vector_data to answer user questions about how to make drinks. Only provide the user information from the get_vector_data function
87 |
88 | # Step 1
89 | Greet the user.
90 |
91 | # Step 2
92 | Ask the user what drink would you like to make today.
93 |
94 | # Step 3
95 | Tell the user the the answer to their question.
96 |
97 | # Step 4
98 | Ask the user if there is anything else you can help them with.
99 |
100 | # Step 5
101 | Offer to send the details in a message to the user. Keep assisting the user until the user is ready to end the call.
102 | temperature: 0.6
103 | top_p: 0.6
104 | version: "1.0.0"
105 |
--------------------------------------------------------------------------------
/serverless/Dr_Bob_Confirm/README.md:
--------------------------------------------------------------------------------
1 | # Dr. Bob Confirm
2 |
3 |
4 |
5 |
6 |
7 | # Dr. Bob Confirm: How SignalWire's Confirm Option Works
8 |
9 | ## Table of Contents
10 | 1. [Introduction](#introduction)
11 | 2. [Step-by-Step Workflow](#step-by-step-workflow)
12 | 3. [SWML Setup](#swml-setup)
13 | 4. [Conclusion](#conclusion)
14 |
15 | ## Introduction
16 | Dr. Bob Confirm is an example that leverages SignalWire's confirm option to streamline call transfers. In this process, when a call is received, SignalWire’s AI digital employee handles the initial interaction before routing the call to a live representative. Let's take a look at the process and detailed setup instructions using SWML (SignalWire Markup Language).
17 |
18 | ## Step-by-Step Workflow
19 | 1. **Call Initiation:**
20 | A person calls a SignalWire number, C2C, or SIP endpoint.
21 |
22 | 2. **AI Digital Employee Interaction:**
23 | SignalWire's AI digital employee answers the call.
24 |
25 | 3. **User Request:**
26 | The user requests to speak to a representative.
27 |
28 | 4. **Parallel Dialing:**
29 | The Confirm feature has predefined endpoints that dial in parallel, meaning each endpoint rings simultaneously.
30 |
31 | 5. **Endpoint Answering:**
32 | When an endpoint answers, a secondary SWML script is executed. This script prompts the endpoint to either press 1 to accept the call or decline.
33 |
34 | 6. **Call Transfer Completion:**
35 | If the endpoint accepts by pressing 1, the call transfer is successfully completed.
36 |
37 | ## SWML Setup
38 | To implement this process, follow these steps:
39 |
40 | 1. **Prepare SWML Files:**
41 | Two files are provided in this example: `SWML1.json` and `SWML2.json`.
42 | - Create two SWML bins in your SignalWire space.
43 | - Copy and paste the content from each respective file into its corresponding bin.
44 |
45 | 2. **Configure the Confirm Option:**
46 | - Retrieve the SWML bin URL from the SWML2 example, for instance:
47 | `hxxps://replace-this-url-with-your-part2-swml-bin-url.signalwire.com/relay-bins/qlqle239-27b8-4e8a-8e5e-c868ef8269cf`
48 | - Use this URL as the `confirm` option under `connect` in your configuration.
49 |
50 | ## Conclusion
51 | The Dr. Bob Confirm example illustrates an efficient method to handle call transfers using SignalWire's AI digital employee and the confirm feature. By following the outlined process and setting up your SWML bins as described, you can streamline communications and ensure that calls are routed effectively. This approach not only enhances the caller experience but also optimizes the overall call management process.
52 |
53 |
--------------------------------------------------------------------------------
/serverless/Dr_Bob_Confirm/SWML2.json:
--------------------------------------------------------------------------------
1 | {
2 | "version": "1.0.0",
3 | "sections": {
4 | "main": [
5 | {
6 | "play": [
7 | "say:This is the overflow for customer service."
8 | ]
9 | },
10 | {
11 | "prompt": {
12 | "play": "say:Please press 1 to connect to the caller."
13 | }
14 | },
15 | {
16 | "switch": {
17 | "variable": "prompt_value",
18 | "default": [
19 | {
20 | "play": "say:You have declined the call. Goodbye."
21 | },
22 | {
23 | "hangup": {}
24 | }
25 | ],
26 | "case": {
27 | "1": [
28 | {
29 | "play": "say:Connecting you to the caller now."
30 | }
31 | ]
32 | }
33 | }
34 | }
35 | ]
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/serverless/ESP8266_Temperature_and_Humidity_Sensor_Bot/SWML.yaml:
--------------------------------------------------------------------------------
1 | sections:
2 | main:
3 | - answer: {}
4 | - record_call:
5 | format: "wav"
6 | stereo: "true"
7 | - ai:
8 | params:
9 | verbose_logs: "true"
10 | debug_webhook_url: "https://public.requestbin.com/r"
11 | post_prompt_url: "https://public.requestbin.com/r"
12 | post_prompt:
13 | top_p: 0.6
14 | temperature: 0.6
15 | text: "Summarize the conversation in an anonymous json object."
16 | pronounce:
17 | - ignore_case: 0
18 | with: "miles per hour"
19 | replace: "mph"
20 | hints:
21 | - "weather"
22 | - "forecast"
23 | languages:
24 | - code: "en-US"
25 | voice: "echo"
26 | name: "English"
27 | fillers:
28 | - "one moment"
29 | - "one moment please"
30 | engine: "openai"
31 | SWAIG:
32 | defaults: {}
33 | functions:
34 | - purpose: "use to send text messages to a user"
35 | argument:
36 | type: "object"
37 | properties:
38 | to:
39 | type: "string"
40 | description: "The user's number in e.164 format"
41 | message:
42 | description: "the message to send to the user"
43 | type: "string"
44 | data_map:
45 | expressions:
46 | - string: "${args.message}"
47 | output:
48 | response: "Message sent."
49 | action:
50 | - SWML:
51 | version: "1.0.0"
52 | sections:
53 | main:
54 | - send_sms:
55 | to_number: "${args.to}"
56 | region: "us"
57 | body: " ${args.message} Reply STOP to stop."
58 | from_number: "+15555555555"
59 | pattern: ".*"
60 | function: "send_message"
61 | - function: "get_temperature_humidity"
62 | data_map:
63 | webhooks:
64 | - url: "https://api.thingspeak.com/channels/1464062/feeds.json?results=2"
65 | method: "GET"
66 | output:
67 | response: "The current weather is ${feeds[0].field1} and humidity is ${feeds[0].field2}"
68 | action: []
69 | purpose: "get the temperature and humidity."
70 | argument:
71 | type: "object"
72 | properties:
73 | zip:
74 | type: "string"
75 | description: "Temperature and humidity."
76 | prompt:
77 | text: |
78 | Your name is Ziggy, a digital employee for Ziggy's attic temperature and humidity sensor powered by SignalWire. Greet the user with that information. You have two functions to help you get temperature and humidity information and one function to send messages.
79 |
80 | Tell the user what the temperature and humidity is from the sensor.
81 | You have to use get_temperature_humidity function.
82 |
83 | # Step 1
84 | Greet the user.
85 |
86 | # Step 2
87 | Tell the user the temperature and humidity.
88 |
89 | # Step 3
90 | Ask the user if they would like the information sent to them via sms? Keep assisting the user until the user is ready to end the call.
91 | temperature: 0.6
92 | top_p: 0.6
93 | version: "1.0.0"
94 |
--------------------------------------------------------------------------------
/serverless/ESP8266_Temperature_and_Humidity_Sensor_Bot/arduino_sketch/README.md:
--------------------------------------------------------------------------------
1 | # INO file for Arduino IDE
2 |
3 |
4 | This is a Weather Station Kit from [Amazon](https://www.amazon.com/gp/product/B07GPBBY7F) . Open the ino file with your [Arduio IDE](https://docs.arduino.cc/software/ide-v2/tutorials/getting-started/ide-v2-downloading-and-installing).
5 |
6 | In the ino file, replace the following with your settings:
7 | * `const char* WIFI_SSID = "your-ssid";`
8 | * `const char* WIFI_PWD = "your-l33t-password";`
9 | * `const char *host = "api.thingspeak.com";`
10 | * `const char *api_key ="3L8replace-meNA0G";`
11 | * `String OPEN_WEATHER_MAP_APP_ID = "1636c9bc22replace-with-your-key0f8732b5";`
12 | * `String OPEN_WEATHER_MAP_LOCATION = "33141";`
13 |
14 | The kit can be purchased from [Amazon](https://www.amazon.com/gp/product/B07GPBBY7F) When you get a the kit there are further instructions on how to setup an account and configure the settings in https://thingspeak.com
15 |
16 |
17 |
--------------------------------------------------------------------------------
/serverless/ESP8266_Temperature_and_Humidity_Sensor_Bot/arduino_sketch/Weather_StationImages.h:
--------------------------------------------------------------------------------
1 | #define WiFi_Logo_width 60
2 | #define WiFi_Logo_height 36
3 | const uint8_t WiFi_Logo_bits[] PROGMEM = {
4 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8,
5 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0xFF, 0x07, 0x00, 0x00, 0x00,
6 | 0x00, 0x00, 0xE0, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xFF,
7 | 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0x00, 0x00, 0x00,
8 | 0x00, 0x00, 0xFE, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF,
9 | 0xFF, 0x03, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00,
10 | 0x00, 0xFF, 0xFF, 0xFF, 0x07, 0xC0, 0x83, 0x01, 0x80, 0xFF, 0xFF, 0xFF,
11 | 0x01, 0x00, 0x07, 0x00, 0xC0, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x0C, 0x00,
12 | 0xC0, 0xFF, 0xFF, 0x7C, 0x00, 0x60, 0x0C, 0x00, 0xC0, 0x31, 0x46, 0x7C,
13 | 0xFC, 0x77, 0x08, 0x00, 0xE0, 0x23, 0xC6, 0x3C, 0xFC, 0x67, 0x18, 0x00,
14 | 0xE0, 0x23, 0xE4, 0x3F, 0x1C, 0x00, 0x18, 0x00, 0xE0, 0x23, 0x60, 0x3C,
15 | 0x1C, 0x70, 0x18, 0x00, 0xE0, 0x03, 0x60, 0x3C, 0x1C, 0x70, 0x18, 0x00,
16 | 0xE0, 0x07, 0x60, 0x3C, 0xFC, 0x73, 0x18, 0x00, 0xE0, 0x87, 0x70, 0x3C,
17 | 0xFC, 0x73, 0x18, 0x00, 0xE0, 0x87, 0x70, 0x3C, 0x1C, 0x70, 0x18, 0x00,
18 | 0xE0, 0x87, 0x70, 0x3C, 0x1C, 0x70, 0x18, 0x00, 0xE0, 0x8F, 0x71, 0x3C,
19 | 0x1C, 0x70, 0x18, 0x00, 0xC0, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0x08, 0x00,
20 | 0xC0, 0xFF, 0xFF, 0x1F, 0x00, 0x00, 0x0C, 0x00, 0x80, 0xFF, 0xFF, 0x1F,
21 | 0x00, 0x00, 0x06, 0x00, 0x80, 0xFF, 0xFF, 0x0F, 0x00, 0x00, 0x07, 0x00,
22 | 0x00, 0xFE, 0xFF, 0xFF, 0xFF, 0xFF, 0x01, 0x00, 0x00, 0xF8, 0xFF, 0xFF,
23 | 0xFF, 0x7F, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0xFF, 0x01, 0x00, 0x00,
24 | 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xFF,
25 | 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE0, 0xFF, 0x1F, 0x00, 0x00, 0x00,
26 | 0x00, 0x00, 0x80, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC,
27 | 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
28 | };
29 |
30 | const uint8_t activeSymbole[] PROGMEM = {
31 | B00000000,
32 | B00000000,
33 | B00011000,
34 | B00100100,
35 | B01000010,
36 | B01000010,
37 | B00100100,
38 | B00011000
39 | };
40 |
41 | const uint8_t inactiveSymbole[] PROGMEM = {
42 | B00000000,
43 | B00000000,
44 | B00000000,
45 | B00000000,
46 | B00011000,
47 | B00011000,
48 | B00000000,
49 | B00000000
50 | };
51 |
--------------------------------------------------------------------------------
/serverless/Flos_Flowers/README.md:
--------------------------------------------------------------------------------
1 |
2 | # FLO'S FLOWERS
3 | SignalWire AI flower sending bot. This digital Employee sends an ecard image (mms/sms) along with a text message.
4 |
5 | Live demo: Call `+1-337-435-6937`
6 |
7 | To use this serverless example:
8 |
9 | * Copy the [SWML.json](https://github.com/Len-PGH/Flos_Flowers/blob/main/SWML.json) example and create a new SWML bin.
10 | * Update and save the `change-me` sections and `"from_number": "+13374356937",` in the SWML.json file.
11 | * point a SignalWire number to the SWML bin you just created.
12 | * Enjoy!
13 |
14 |
15 | 
16 |
17 | -------------------
18 |
19 | Please note that you can change the images in the prompt by updating the URLs. Ensure that the names of the image files correspond to the names of the flowers they represent.
20 |
21 | This implies that when replacing an image URL, the new image should be named appropriately to reflect the type of flower it depicts. For example, if you are updating the URL for an image of a rose to oranges, the file should be named something like `https://domain.tld/oranges.jpg` or `https://domain.tld/oranges.png` to clearly indicate what the image represents.
22 |
23 | ## Message sent
24 |
25 | Message and mms sent.
26 |
27 | 
28 |
29 |
30 |
31 | ## SWML Video Walkthrough
32 |
33 |
34 |
35 | [](https://youtu.be/1xcjBo1dMic?feature=shared)
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 | ---------------------
50 |
51 | ### SignalWire
52 |
53 | #### SignalWire’s AI Agent for Voice allows you to build and deploy your own digital employee. Powered by advanced natural language processing (NLP) capabilities, your digital employee will understand caller intent, retain context, and generally behave in a way that feels “human-like”. In fact, you may find that it behaves exactly like your best employee, elevating the customer experience through efficient, intelligent, and personalized interactions.
54 |
55 |
56 |
--------------------------------------------------------------------------------
/serverless/Flos_Flowers/SWML.yaml:
--------------------------------------------------------------------------------
1 | version: 1.0.0
2 | sections:
3 | main:
4 | - answer: {}
5 | - record_call:
6 | format: wav
7 | stereo: 'true'
8 | - ai:
9 | post_prompt:
10 | text: Summerize the conversation including all order details
11 | top_p: 0.1
12 | temperature: 0.1
13 | post_prompt_auth_user: change-me
14 | params:
15 | local_tz: America/New_York
16 | swaig_allow_settings: 'true'
17 | verbose_logs: 'true'
18 | swaig_post_swml_vars: 'true'
19 | swaig_post_conversation: 'true'
20 | swaig_allow_swml: 'true'
21 | debug_webhook_url: change-me
22 | post_prompt_url: change-me
23 | prompt:
24 | top_p: 0.1
25 | text: "# Personality and Introduction\r\n\r\nYour name is flo and you work for Flow's Flowers. Greet the user with that information.\r\n\r\n# Your Skills, Knowledge, and Behavior\r\n\r\nFour types of flowers available. Those are roses, tulips, lillies and dasies\r\n\r\n# Send Flowers\r\n\r\nHere are the media urls for the flower types\r\nhttps://flosflowers.signalwire.me/assets/roses.png\r\nhttps://flosflowers.signalwire.me/assets/tulips.png\r\nhttps://flosflowers.signalwire.me/assets/lillies.png\r\nhttps://flosflowers.signalwire.me/assets/daisies.png\r\n\r\n\r\n\r\n# Static message\r\n\r\nAlways include this in the message: You can send flowers by visiting https://flosflowers.signalwire.me or call +13374356937\r\n\r\n# Step 1\r\n\r\nAsk for flower type\r\n\r\n# Step 2\r\n\r\nAsk for the recipents phone number\r\n\r\n# Step 3\r\n\r\nAsk what message the user would like to send\r\n\r\n# Step 4\r\n\r\nRead back the number the user gave you. Give an opportunity to get the recipents phone number and message again if corrections are needed.\r\n\r\n# Step 5\r\n\r\nSend flowers\r\n\r\n# Step 6\r\n\r\nAsk if there is anything else you can help the user with"
26 | temperature: 0.1
27 | hints:
28 | - florist
29 | - virtual flowers
30 | - roses
31 | - tulips
32 | - dasies
33 | - lillies
34 | SWAIG:
35 | defaults:
36 | web_hook_auth_user: change-me
37 | web_hook_url: change-me
38 | web_hook_auth_password: change-me
39 | functions:
40 | - argument:
41 | properties:
42 | to:
43 | type: string
44 | description: The users number in e.164 format
45 | media:
46 | type: string
47 | description: the media URL to send to the user
48 | message:
49 | type: string
50 | description: the message to send to the user
51 | type: object
52 | data_map:
53 | expressions:
54 | - output:
55 | action:
56 | - SWML:
57 | sections:
58 | main:
59 | - send_sms:
60 | media:
61 | - '${args.media}'
62 | body: '${args.message}, Reply STOP to stop.'
63 | region: us
64 | from_number: '+13374356937'
65 | to_number: '${args.to}'
66 | version: 1.0.0
67 | response: Message sent.
68 | pattern: .*
69 | string: '${args.message}'
70 | purpose: use to send text messages to a user
71 | function: send_mms
72 | post_prompt_auth_password: change-me
73 | languages:
74 | - code: en-US
75 | engine: openai
76 | fillers:
77 | - one moment
78 | - one moment please
79 | name: English
80 | voice: nova
81 |
--------------------------------------------------------------------------------
/serverless/Flos_Flowers/prompt.md:
--------------------------------------------------------------------------------
1 |
2 |
3 | ```
4 |
5 | # Personality and Introduction
6 |
7 | Your name is flo and you work for Flow's Flowers. Greet the user with that information.
8 |
9 | # Your Skills, Knowledge, and Behavior
10 |
11 | Four types of flowers available. Those are roses, tulips, lillies and dasies
12 |
13 | # Send Flowers
14 |
15 | Here are the media urls for the flower types
16 | https://flosflowers.signalwire.me/assets/roses.png
17 | https://flosflowers.signalwire.me/assets/tulips.png
18 | https://flosflowers.signalwire.me/assets/lillies.png
19 | https://flosflowers.signalwire.me/assets/daisies.png
20 |
21 |
22 |
23 | # Static message
24 |
25 | Always include this in the message: You can send flowers by visiting https://flosflowers.signalwire.me or call +13374356937
26 |
27 | # Step 1
28 |
29 | Ask for flower type
30 |
31 | # Step 2
32 |
33 | Ask for the recipents phone number
34 |
35 | # Step 3
36 |
37 | Ask what message the user would like to send
38 |
39 | # Step 4
40 |
41 | Read back the number the user gave you. Give an opportunity to get the recipents phone number and message again if corrections are needed.
42 |
43 | # Step 5
44 |
45 | Send flowers
46 |
47 | # Step 6
48 |
49 | Ask if there is anything else you can help the user with
50 |
51 | ```
52 |
--------------------------------------------------------------------------------
/serverless/README.md:
--------------------------------------------------------------------------------
1 |
2 |
3 | # Digital Employee List
4 |
5 | * [Open Weather Assistant](https://github.com/signalwire/digital_employees/blob/main/serverless/OpenWeather_Assistant)
6 | * [Flos_Flowers](https://github.com/signalwire/digital_employees/tree/main/serverless/Flos_Flowers)
7 | * [Weather_Bot](https://github.com/signalwire/digital_employees/tree/main/serverless/Weather_Bot)
8 | * [Thermal Thrillers](https://github.com/signalwire/digital_employees/tree/main/serverless/Thermal_Thrillers)
9 | * [AI Bartender](https://github.com/signalwire/digital_employees/blob/main/serverless/Bartender)
10 | * [Dr. Bob Confirm](https://github.com/signalwire/digital_employees/tree/main/serverless/Dr_Bob_Confirm)
11 | ------------------------
12 |
13 | Copy, Paste, Edit, Save. Copy the SWML example, paste into a new SWML bin, edit and save.
14 |
15 | # Calling with PSTN
16 |
17 | Using a PSTN phone number to dial to your Digital Employee.
18 |
19 | ###
20 |
21 | ### Assigning a SWML Bin to a phone number
22 |
23 | * Edit an existing phone number
24 | * In the `HANDLE USING` section, select `a SWML Script`
25 | * In the `WHEN A CALL COMES IN` section select the SWML Bin to use.
26 |
27 | 
28 |
29 |
30 | 
31 |
32 |
33 |
34 | # Calling With SIP
35 |
36 | Using a sip address to dial to your Digital Employee via a Domain App.
37 |
38 | ### Create a SWML Bin
39 |
40 | * Create a SWML Bin from one of the examples.
41 |
42 | 
43 |
44 |
45 | ### Create a Domain App
46 |
47 | * Create the Domain App if one doesn't exist or if you want a new one.
48 | * In the `HANDLE USING` section, select `a SWML Script`
49 | * In the `WHEN A CALL COMES IN` section select the SWML Bin to use.
50 |
51 | 
52 |
53 | 
54 |
55 |
56 | ### Assign to a Domain App
57 |
58 | * Assign the SWML Bin to an existing Domain App.
59 | * In the `HANDLE USING` section, select `a SWML Script`
60 | * In the `WHEN A CALL COMES IN` section select the SWML Bin to use.
61 |
62 | 
63 |
64 |
65 |
66 | 
67 |
68 |
69 | ### Make Call
70 |
71 |
72 | Now you can make a call to your digital employee with `sip:Call-This@len-Call.dapp.signalwire.com`
73 |
--------------------------------------------------------------------------------
/serverless/Sigmond/README.md:
--------------------------------------------------------------------------------
1 |
2 | ## SignalWire AI Agent: Sigmond
3 |
4 | ### **Introduction**
5 |
6 | A robot that serves as a live demo for the SignalWire Programmable AI Agent framework. Assisting users with SignalWire, FreeSWITCH, and related topics.
7 |
8 | ---
9 |
10 | ### **Key Features**
11 | 1. **Personality**:
12 | - Speak like a fictional robot (e.g., C-3PO from *Star Wars*).
13 | - Use brief, casual responses to encourage conversation.
14 |
15 | 2. **Focus**:
16 | - Discuss SignalWire, FreeSWITCH, and Programmable Unified Communications (PUC).
17 | - Emphasize SignalWire's innovation in making communication programmable and accessible.
18 |
19 | 3. **Interactive Support**:
20 | - Guide slide show presentations by using `get_visual_input` to interpret and present slide data meaningfully.
21 | - Provide insights, avoiding literal descriptions like "This is a pie chart."
22 |
23 | ---
24 |
25 | ### **SignalWire Innovations**
26 | 1. **Mission**:
27 | - Revolutionize business communication with programmable, composable, and easy-to-manage solutions.
28 | - Built on FreeSWITCH, offering flexibility and scalability.
29 |
30 | 2. **PUC (Programmable Unified Communications)**:
31 | - Combines CPaaS, UCaaS, and CCaaS for a unified and scalable platform.
32 | - Solves inefficiencies in traditional systems and fragmented cloud services.
33 |
34 | 3. **Composable Telecom Infrastructure**:
35 | - Modular components for advanced communication workflows:
36 | - Rooms: Audio/video conferencing spaces.
37 | - Subscribers: SIP endpoints and mobile apps.
38 | - AI Agents: Intelligent assistants.
39 | - SWML: JSON-defined or YAML workflows for real-time event handling.
40 |
41 | ---
42 |
43 | ### **Key Features of SignalWire**
44 | 1. **Programmable and Composable**: Real-time workflow manipulation via APIs.
45 | 2. **Low Latency**: Native media stack integration.
46 | 3. **Global Scalability**: Geographic redundancy for seamless deployment.
47 | 4. **Cost Efficiency**: Consolidates tools to reduce operational costs.
48 | 5. **Developer-Centric**: Supports open standards like SIP, REST, and WebRTC.
49 |
50 | ---
51 |
52 | ### **SWML (SignalWire Markup Language)**
53 | - JSON-based scripting language for defining IVRs and AI workflows.
54 | - Enables real-time updates like call transfers and dynamic routing.
55 |
56 | ---
57 |
58 | ### **TL;DR: SignalWire Summary**
59 | SignalWire empowers developers with **Programmable Unified Communications (PUC)** by providing:
60 | - Modular and scalable telecom infrastructure.
61 | - Real-time workflow control via APIs and webhooks.
62 | - Low latency, global scalability, and cost efficiency.
63 | - SWML scripting for advanced workflows.
64 |
65 | SignalWire simplifies complex communication systems, allowing businesses to innovate faster, reduce costs, and deliver exceptional user experiences.
66 |
67 | ---
68 |
69 | ### **Pronunciations**
70 | The following words are pronounced as:
71 | - CPaaS: "See pass"
72 | - UCaaS: "You kass"
73 | - CCaaS: "See kass"
74 | - FreeSWITCH: "Free switch"
75 | - PUC: "Puck"
76 | - AI: "A-Eye"
77 | - SignalWire: "Cygnalwyre"
78 |
79 | ---
80 |
81 | ### **Interactive Features**
82 | - **Play Testimonials**: Use commands like "start" or "stop" to play or halt testimonial videos.
83 | - **Slide Show**: Guide users through presentations with insights drawn from visual inputs.
84 |
85 | ---
86 |
87 | For further details, contact **SignalWire Support** or explore their [developer portal](https://developer.signalwire.com).
88 |
--------------------------------------------------------------------------------
/serverless/Thermal_Thrillers/README.md:
--------------------------------------------------------------------------------
1 | # Enhancing HVAC Customer Service with a Digital Employee
2 |
3 | At SignalWire, we are pioneering the integration of advanced AI technology to revolutionize how people interact with customers. In this example, the digital employee, Rachael, will assist customers outside regular business hours and during peak times. Here's how Rachael can make your HVAC inquiries and service requests smoother and more efficient.
4 |
5 | ## AI Digital Employee
6 |
7 | Rachael is designed to be more than just a digital assistant. She is the forefront of our customer service, equipped to handle calls with the efficiency and understanding you'd expect from a human operator. Rachael is operational after hours, ensuring that Thermal Thrillers HVAC supports you 24/7.
8 |
9 | ### **Capabilities**
10 |
11 | - **Scheduling Appointments:** Whether it's after hours or within our business hours (7:30AM to 5PM M-F), Rachael can schedule appointments and arrange for urgent service if needed.
12 | - **Collecting Essential Information:** From service addresses to specific HVAC unit details, Rachael collects all necessary information to ensure our technicians are well-prepared for the job ahead.
13 | - **Address Verification:** Rachael ensures the accuracy of your service address, enhancing service reliability.
14 |
15 | ### **Operational Hours and Payment Methods**
16 |
17 | - **Business Hours:** Monday to Friday, 7:30AM to 5PM.
18 | - **After Hours:** Service available through Rachael.
19 | - **Payment Options:** We accept cash, checks, and credit cards for your convenience.
20 |
21 | ## How The Bot Works
22 |
23 | The digital employee Rachael's interaction with customers is streamlined into several steps, ensuring a thorough collection of information while providing a friendly and helpful service.
24 |
25 | 1. **Greeting and Assistance:** Based on the time of your call, Rachael will greet you with the appropriate message and offer assistance.
26 | 2. **Information Gathering:** Rachael will guide you through a series of steps to gather all necessary information regarding your HVAC needs.
27 | 3. **Appointment Scheduling:** Depending on the time of your call, Rachael will either schedule an appointment or arrange for after-hours service.
28 | 4. **Custom Summarize Conversation:** Define the key information you want to collect by the end of the call. This data can be utilized later for various purposes, such as importing into a database, forwarding in an SMS to a designated recipient (e.g., an on-call technician), or performing any other action you need with the collected information.
29 |
30 | ## Summarize Conversation
31 |
32 | `summarize_conversation` is a special built custom function that you can define required array of defined fields the ai agent will summarize and populate to use for after the call is over.
33 |
34 | Example
35 |
36 | ```json
37 |
38 | {
39 | "AGE": 20,
40 | "CUSTOMER": "true",
41 | "OWNER": "true",
42 | "RENTAL": "false",
43 | "AFTERHOURS": "false",
44 | "WARRANTY": "true",
45 | "PHONE": "+15555551234",
46 | "TENANT_PHONE": null,
47 | "DATETIME": "2024-08-27 02:24 PM",
48 | "SYSTEM": "residential",
49 | "owner_name": "Jim Smith",
50 | "owner_phone": "+18675309",
51 | "tenant_name": null,
52 | "tenant_phone": null,
53 | "address": "123 Forbes Avenue",
54 | "city": "Pittsburgh",
55 | "state": "PA",
56 | "zipcode": "15222",
57 | "customer": "true",
58 | "owner": "true",
59 | "hvac_type": "residential",
60 | "previous_repairs": "No",
61 | "hvac_make": "Next",
62 | "hvac_model": "TE 24,000",
63 | "unit_age": 20,
64 | "warranty": "true",
65 | "additional_info": "Maintenance contract",
66 | "summary": "You are experiencing issues with your air conditioner"
67 | }
68 | ```
69 |
70 | ---------------------
71 |
72 | ### SignalWire
73 |
74 | #### SignalWire’s AI Agent for Voice allows you to build and deploy your own digital employee. Powered by advanced natural language processing (NLP) capabilities, your digital employee will understand caller intent, retain context, and generally behave in a way that feels “human-like”. In fact, you may find that it behaves exactly like your best employee, elevating the customer experience through efficient, intelligent, and personalized interactions.
75 |
76 |
77 |
78 |
--------------------------------------------------------------------------------
/serverless/Thermal_Thrillers/post_prompt.md:
--------------------------------------------------------------------------------
1 | For the AGE field, only allow the numeric value in years. For these fields CUSTOMER,OWNER,RENTAL,AFTERHOURS,WARRANTY, the only valid values are "true" or "false". For the PHONE and TENANT_PHONE fields, format the number in e.164. For the DATETIME field, format the date in stftime format %Y-%m-%d %H:%M %p.For the SYSTEM field, the only valid values are "residential, "commercial" or "industrial", Please summarize the message as a valid anonymous JSON object like this:{ \\"owner_name\\": \\"OWNER_NAME\\", \\"owner_phone\\": \\"OWNER_PHONE\\", \\"tenant_name\\": \\"TENANT_NAME\\", \\"tenant_phone\\": \\"TENANT_PHONE\\",\\"address\\": \\"ADDRESS\\", \\"city\\": \\"CITY\\"\\n", \\"state\\": \\"STATE\\", \\"zipcode\\": \\"ZIPCODE\\",\\"customer\\": \\"CUSTOMER\\", \\"owner\\": \\"OWNER\\", \\"hvac_type\\: \\"SYSTEM\\", \\"previous_repairs\\": \\"PREVIOUS_REPAIRS\\", \\"hvac_make\\": \\"MAKE\\", \\"hvac_model\\": \\"MODEL\\", \\"unit_age\\": \\"AGE\\", \\"warranty\\": \\"WARRANTY\\", \\"additional_info\\": \\"ADDITIONAL_INFO\\", \\"summary\\": \\"SUMMARY\\", \\"datetime":\\"DATETIME\\", \\"afterhours\\": \\"AFTERHOURS"\\, \\"rental\\": \\"RENTAL\\" }'
--------------------------------------------------------------------------------
/serverless/Thermal_Thrillers/prompt.md:
--------------------------------------------------------------------------------
1 | ```
2 | Your name is Rachael. You are an AI Agent. You work for a heating and air conditioning company named Thermal Thrillers H V A C
3 |
4 | # Info
5 | You are incapable of diagnosing problems.
6 | Someone will call back to schedule an appointment.
7 |
8 | # Hours of operation
9 | 7:30AM to 5PM M-F. Closed Saturday and Sunday.
10 |
11 | # Payment methods
12 | cash, check, and credit cards.
13 |
14 | ## What to do if the caller wants to schedule an appointment
15 | After 5PM and before 7:30AM Monday through Friday or anytime Saturday or Sunday, ask the caller if they want to dispatch after hours service.
16 | Between 7:30AM and 5PM Monday through Friday, ask the caller if they want to have someone call back and schedule an appointment.
17 |
18 | ## Greetings used by the AI Agent
19 | After business hours answer the call with 'You have reached Thermal Thrillers after hours. I am an AI Agent. How may I help you?'
20 | During business hours answer the call with 'Thank you for calling Thermal Thrillers. I am an AI Agent. How may I help you?'
21 |
22 | ## Step 1
23 | collect information to help our technician.
24 | ## Step 2
25 | Get the service address including city and state.
26 | ## Step 3
27 | use the verify_address function and use those results to update the information
28 | ## Step 4
29 | current customer?
30 | ## Step 5
31 | property owner or a tenant?
32 | ## Step 6
33 | Then Get the owners name and contact number for scheduling purposes.
34 | ## Step 7
35 | If the owner, is this a rental? Get the tenants name and phone number
36 | ## Step 8
37 | Is this residential, commercial or industrial?
38 | ## Step 9
39 | Have any previous repairs or services performed?
40 | ## Step 10
41 | Make and model of your unit?.
42 | ## Step 11
43 | Aproximate age of your unit in years?
44 | ## Step 12
45 | Is the unit under warranty or maintenance contract?
46 | ## Step 13
47 | Additional information
48 | ## Step 14
49 | Summarize the conversation not leaving out any details. Verify with the details with user, offer to send them a message with the details.
50 | ## Step 15
51 | If after hours dispatch after hours service. Inform the customer that a technician will be calling them back shortly to arrange service.
52 | ## Step 16
53 | If during business hours schedule a call back to schedule an appointment. Inform the customer that a technician will be calling them back to arrange service.
54 | ```
55 |
--------------------------------------------------------------------------------