Theme
Notifications and messaging Preview
All five messaging functions work on the Connector. Two of them, SendMail and NotifyViaTelegramBot, need configuring once in System, then Settings before they will send anything; the other three take their credentials as arguments.
| Function | Needs configuring first |
|---|---|
SendMail | Yes, the SMTP tab |
NotifyViaTelegramBot | Yes, the Telegram tab |
SendToSlackWebHook | No |
SendToTeamsWebHook | No |
SendSMSViaTwilio | No |
Every one of them returns a boolean and none of them throws, so an unchecked call fails silently. Check the return value.
Slack
js
function SendToSlackWebHook(webhookURL, message, sender?, icon?): boolean;Posts to a Slack incoming webhook. sender is a display name and icon is an emoji shortcode.
js
SendToSlackWebHook(
slackWebhookUrl,
CtxUsername() + " uploaded " + CtxRelPath() + " to " + CtxVFSName(),
"SFTP.cloud Connector",
":inbox_tray:"
);Returns true only when Slack answered with ok.
Microsoft Teams
js
function SendToTeamsWebHook(webhookURL, message): boolean;Posts plain text to a Teams incoming webhook, using the simple {"text": "..."} payload that renders as a basic card.
js
SendToTeamsWebHook(teamsWebhookUrl, "Nightly export complete: " + fileCount + " files.");For a richer Adaptive Card, post it yourself with HttpCli, keeping the request body limitation in mind.
SMS through Twilio
js
function SendSMSViaTwilio(accountSid, authToken, fromNumber, toNumber, message): boolean;Credentials are arguments rather than configuration, so this works on the Connector without anything being set up centrally.
js
SendSMSViaTwilio(twilioSid, twilioToken, "+12345678901", "+15550005555",
"Quarantine triggered on " + CtxVFSName());Recipient numbers are in international format. true means Twilio accepted the message, not that it was delivered; delivery status lives in your Twilio console.
Email
js
function SendMail(from, to, subject, body, attachment?): boolean;Sends through the relay configured on the SMTP tab of System, then Settings. That is your own mail server, sending as you, from your address; SFTP.cloud never sees the message and never sends it for you. Configure it before your first script needs it, and use Send test message on that tab to prove it works.
| Argument | Notes |
|---|---|
from | The sender. Leave it empty to use the address configured on the SMTP tab, which is usually what you want |
to | One address, or several separated by ; |
subject | Plain text |
body | Plain text. There is no HTML option |
attachment | Optional. A path to a file on the Connector, not a path inside a virtual file system |
js
// after.upload, Run in the background, timeout 30000
if (CtxRelPath().indexOf("/inbound/invoices/") === 0) {
var sent = SendMail("", "ap@example.com",
"New invoice from " + CtxUsername(),
"File: " + CtxRelPath() + "\nVirtual file system: " + CtxVFSName());
if (!sent) {
Log.Error("could not send the invoice notification");
}
}Returns true when the relay accepted the message, which is not the same as it reaching the recipient. Delivery after that point is between your mail server and theirs.
Attachments come from the Connector's own disk
The fifth argument is a local path. To attach a file that lives in a virtual file system, download it to a local temporary directory first with the VFS object, attach that copy, and delete it afterwards.
A relay that is off is not an error your script sees
If SMTP is switched off or was never configured, SendMail returns false and writes the reason to the log. The script keeps running. This is the one to check the return value on, because a notification that silently never sends is exactly the kind of thing nobody notices for months.
Telegram
js
function NotifyViaTelegramBot(message): boolean;Posts to every chat listed on the Telegram tab of System, then Settings. You supply a bot token from BotFather and one or more chat ids; the Connector posts, and nothing else.
js
NotifyViaTelegramBot("Quarantine triggered on " + CtxVFSName() + " by " + CtxUsername());The bot only sends
It never reads messages and never accepts commands, so nobody can drive your Connector by messaging the bot. If you know Syncplify Server's Telegram integration, which does accept /status and /restart, this is deliberately not that.
Returns true only when every configured chat accepted the message. A stale chat id makes it return false, and the log names which one, but the other chats still receive it.
Where the credentials live
The SMTP password and the Telegram bot token are configuration: you enter them once in Settings and they are stored encrypted, never displayed again.
The other three take their credentials as arguments, which means a Slack webhook URL, a Teams connector URL and a Twilio auth token would otherwise sit in your script source. Put them in the secret store instead:
js
var hook = GetSecret("slack-alerts-webhook");
SendToSlackWebHook(hook, CtxUsername() + " uploaded " + CtxRelPath(), "SFTP.cloud", ":inbox_tray:");A webhook URL is a credential
Anyone holding a Slack or Teams webhook URL can post into that channel as your integration, forever, until somebody rotates it. Anyone holding a Twilio token can send messages you pay for. Keeping them in the secret store means they are not in the script source, not in a script export, and not readable in a database backup.
It does not make them invisible to your own administrators: anyone who can write a script here can read any secret. See what the store does and does not protect you from.
Notifications belong on after handlers
WARNING
A notification is not worth delaying a transfer for, and it is certainly not worth refusing one. Put it on an after handler marked Run in the background. Slack being slow then costs nothing; on a fail closed before handler it would cost you your uploads.
js
// after.upload, Run in the background, timeout 15000
var quarantined = CtxRelPath().indexOf("/quarantine/") === 0;
if (quarantined) {
SendToSlackWebHook(slackWebhookUrl,
"Quarantined file from " + CtxUsername() + ": " + CtxRelPath(),
"SFTP.cloud", ":rotating_light:");
}