Skip to navigation

Deploy SWML from web servers

Serve SWML scripts from web servers and Relay applications
View as MarkdownOpen in Claude

SWML scripts can be served in multiple ways beyond the SignalWire Dashboard. This guide covers serving SWML from web servers and Relay applications.

For complete information about variables, the Call Object, and all variable scopes, see the Variables and Expressions reference.

The examples below use Calling SWML (the voice-call flavor). The same deployment patterns apply to Messaging SWML for inbound SMS and MMS — the only difference is the webhook payload shape (message instead of call) and the set of available methods.

From a web server

This use case is described in detail in the Handling Incoming Calls from Code guide.

In the phone number settings, when you check the “Use External URL for SWML Script handler?” option, you can set a Web URL that will serve the SWML script. Every time a call comes in (or some other designated event occurs), SignalWire sends a POST request to the URL using the standard document-fetching webhook format. The request body contains the call object, vars, params, and envs. See the document-fetching webhook reference for the full request body structure.

Understanding the POST Request

The vars object and the params object will be empty for a new call. If you’re executing a remote SWML script using the execute or transfer methods, the vars parameter has a list of the variables declared in the script so far. And the params object has the list of parameters explicitly set by the execute or transfer methods.

You can also reference the properties of call and params objects during the script execution using the variable subtitution bracket like so:

version: 1.0.0
sections:
main:
- play:
url: 'say:%{call.from}'

Further, consider the following SWML script:

version: 1.0.0
sections:
main:
- play:
url: '%{params.file}'
- return: 1

It references params.file in its play method. If this SWML was invoked as a response to a phone call, it would cause an error as the params object is empty. But if it was hosted on a server and called with the execute or the transfer method, the params object is passed into the SWML.

The SWML above can be invoked as follows:

version: 1.0.0
sections:
main:
execute:
dest: https://example.com/swml.yaml
params:
file: https://cdn.signalwire.com/swml/audio.mp3

From a Relay application

You can also execute SWML from a Relay application. The following handler uses the Relay client in the Server SDKs.

# Install: python -m pip install signalwire-sdk==3.4.1
# Save as swml_relay.py and run: python swml_relay.py
from signalwire.relay import RelayClient
SCRIPT = """
version: 1.0.0
sections:
main:
- answer: {}
- execute:
dest: play_music
params:
to_play: 'https://cdn.signalwire.com/swml/April_Kisses.mp3'
play_music:
- play:
url: '%{params.to_play}'
"""
client = RelayClient(
project="<YOUR_PROJECT_ID>",
token="<YOUR_API_TOKEN>",
contexts=["swml"],
)
@client.on_call
async def handle_call(call):
await call.transfer(SCRIPT)
client.run()

The handler subscribes to the topic swml, so it receives every call to a phone number whose call handler is a Relay Application with that topic. You set a number’s handler under Inbound Call Settings on the number’s page in the SignalWire Dashboard. When a call arrives, the handler transfers it to the SWML document, which takes over the call. The transfer destination can be an inline SWML document, as here, or the URL of a server that returns one.

Next steps