GAMMU-SMSD-RUN(7)
π GAMMU-SMSD-RUN(7) β the RunOnReceive glow-up guide π
okay so this is the <pink>Gammu</pink> manual page for gammu-smsd-run, and it's literally all about the RunOnReceive directive. bestie, if you've ever wanted SMSD to do stuff the second a message lands, this is your page. let's get into it π«Ά
β¨ NAME β¨
gammu-smsd-run β the documentation for the RunOnReceive directive. that's it, that's the name, slay.
πΈ DESCRIPTION πΈ
so <hotpink>Gammu SMSD</hotpink> can be set up with the RunOnReceive directive (peep the SMSD Configuration File for the deets) to run a program you choose after it receives every single message. and like, it can receive one message or a whole bunch of messages that are parts of one multipart message. multipart representation, we love to see it π
the command you configure can totally include parameters. SMSD appends the identifiers of the received messages as extra arguments. those identifiers depend on the service backend β typically database row IDs, or file names for the files backend. oh and btw, file names do not include the inbox directory. multipart messages can hand you multiple arguments, so your scripts have to handle all the identifiers they get. no skipping, fr fr.
on POSIX systems, the configured command runs through a shell, so any special characters in that command need escaping. message identifiers get passed as separate literal arguments. SMSD waits for the script to terminate, which means slow scripts can delay receiving new messages π and do not β i repeat, do NOT β rely on a fixed timeout to interrupt a blocked script.
on Windows, SMSD starts the configured executable directly. batch files need an explicit command interpreter, like the example further down ("Running a batch file on Windows"). SMSD does not wait for the process to finish and does not collect its exit status. so hooks can overlap, bestie, and a successful process creation does not mean message forwarding actually succeeded. it's giving "started, not finished" π
Note: on POSIX systems, standard input is closed and standard output and standard error get captured in the SMSD log. on Windows, the hook has to arrange its own output and error logging. scripts should not require interactive input. like, ever. π
π¦ ENVIRONMENT π¦
added in version 1.28.0, iconic behavior.
the program runs with an environment that contains a lot of info about the message. you can use it together with the NULL service (see Null Backend) to implement completely your own processing of messages. main character energy tbh π
β Global variables
SMS_MESSAGESβ number of physical messages received.DECODED_PARTSβ number of decoded message parts.PHONE_IDβ added in version1.38.2. it's the value ofPhoneID. super useful when you're running multiple instances (see Multiple modems). this variable is available to allRunOndirectives, including calls which don't provide message details. versatile queen π
π Per message variables
the variables described as SMS_1_... are generated for each physical message, where 1 is replaced by the current number of the message. ok so:
SMS_1_CLASSβ class of message.SMS_1_NUMBERβ sender number.SMS_1_TEXTβ message text. heads up: text is not available for 8-bit binary messages.SMS_1_REFERENCEβ added in version1.38.5. Message Reference. if a delivery status was received, this variable contains the TPMR of the original message.SMS_1_SENT_IDβ for a delivery report matched by a database backend, the ID of the corresponding row in thesentitemstable. the value is empty for other messages, when no matching sent message was found, and for non-database backends.SMS_1_TIMESTAMPβ message date and time as seconds since the Unix epoch. for a received message this is the service center timestamp. for a delivery report this is the time when the service center received the original message. the value is empty when the message doesn't contain a valid date and time.SMS_1_DATETIMEβ same value asSMS_1_TIMESTAMP, formatted as ISO 8601 with a timezone offset, for example2024-01-02T03:04:05+01:30.SMS_1_SMSC_TIMESTAMPβ for a delivery report, the discharge time as seconds since the Unix epoch. the value is empty for other messages or when the report doesn't contain a valid discharge time.SMS_1_SMSC_DATETIMEβ same value asSMS_1_SMSC_TIMESTAMP, formatted as ISO 8601 with a timezone offset.
π Per part variables
the variables described as DECODED_1_... are generated for each message part, where 1 is replaced by the current number of the part. only the variables whose content is actually present in the message get set. no filler, we respect that π
DECODED_1_TEXTβ decoded long message text.DECODED_1_MMS_SENDERβ sender of MMS indication message.DECODED_1_MMS_TITLEβ title of MMS indication message.DECODED_1_MMS_ADDRESSβ address (URL) of MMS from MMS indication message.
See also: Can I use Gammu to receive MMS?
DECODED_1_MMS_SIZEβ size of MMS as specified in MMS indication message.
π₯ EXAMPLES π₯
πΈ Activating RunOnReceive
to activate this feature you need to set RunOnReceive in the SMSD Configuration File. literally two lines, you got this:
[smsd]
RunOnReceive = /path/to/script.sh
π§ Running a batch file on Windows
use cmd.exe to launch a batch file. for example, with the script and inbox in C:\gammu:
[smsd]
RunOnReceive = C:\Windows\System32\cmd.exe /d /c C:\gammu\forward_sms.bat
adjust these absolute paths so they match your installation, and restart SMSD after changing the configuration. also note the example uses paths without spaces. π
do not add "%FILE%" β that is not a Gammu placeholder. SMSD appends the received file names automatically.
for example, the batch file receives IN20260228_053040_00_+61402111111_00.txt as its first argument. inside the batch file, %1 accesses that argument and %~1 removes surrounding quotes. with the inbox above, the full path is C:\gammu\%~1. and process subsequent arguments too, for example using shift in a loop. don't leave args hanging, bestie π
use absolute paths for the inbox, address book, log files, and helper programs. the hook inherits SMSD's working directory, which does not have to be the script or inbox directory. when you move SMSD to a Windows service, make sure the service account can access these files and any credentials the forwarding program needs. π
to test invocation separately from email delivery, save the following as C:\gammu\receive-test.bat and temporarily use that path in RunOnReceive:
@echo off
setlocal DisableDelayedExpansion
>>C:\gammu\receive-hook.log echo Hook started
>>C:\gammu\receive-hook.log set SMS_MESSAGES
>>C:\gammu\receive-hook.log set SMS_1_NUMBER
restart SMSD and send a fresh SMS. a new entry in receive-hook.log confirms the batch file started. if no entry appears, check the SMSD log for Starting run on receive and CreateProcess failed, and check that the account running SMSD can write the diagnostic log. restore the forwarding script path after testing β and its own log should record processing and email delivery errors, because Windows SMSD does not collect the script's output or exit status. periodt π
π Forwarding messages with an address book
a forwarding program can match SMS_1_NUMBER against the Number column of a CSV address book and use the corresponding Name in the email subject. store and compare phone numbers in a consistent format, for example international numbers beginning with +, and use the sender's number when no name matches. consistency is key, bestie β¨
for multipart text, use the available DECODED_n_TEXT variables described above, or process all file arguments. do not assume SMS_1_TEXT contains the entire message. read message text as data inside the forwarding program rather than expanding it into batch commands β otherwise SMS characters could get interpreted as command syntax, and that's a big yikes π
configure SMTP authentication in the forwarding program. that program is also responsible for logging delivery failures and retaining pending messages for retry. starting a hook does not guarantee email delivery, ngl.
π¦ Processing messages from the files backend
the following script (if used as a RunOnReceive handler) passes message data to another program. this works only with the Files backend:
#!/bin/sh
INBOX=/path/to/smsd/inbox
PROGRAM=/bin/cat
for ID in "$@" ; do
$PROGRAM < $INBOX/$ID
done
β Invoking commands based on message text
the following script (if used as a RunOnReceive handler) executes given programs based on message text. cute lil dispatcher, honestly:
#!/bin/sh
# Check for sender number
if [ "$SMS_1_NUMBER" != "+420123456789" ] ; then
exit
fi
# Handle commands
case "$SMS_1_TEXT" in
"DMS A")
/usr/bin/dms-a
;;
"DMS B")
/usr/bin/dms-b
;;
esac
π Passing message text to program
the following script (if used as a RunOnReceive handler) passes message text and sender to an external program:
#!/bin/sh
PROGRAM=/bin/echo
for i in `seq $SMS_MESSAGES` ; do
eval "$PROGRAM \"\${SMS_${i}_NUMBER}\" \"\${SMS_${i}_TEXT}\""
done
π Passing MMS indication parameters to external program
the following script (if used as a RunOnReceive handler) will write information about each received MMS indication to the log file. just replace the echo command with your own program to do custom processing. swap in your fave and go off π
#!/bin/sh
if [ $DECODED_PARTS -eq 0 ] ; then
# No decoded parts, nothing to process
exit
fi
if [ "$DECODED_1_MMS_ADDRESS" ] ; then
echo "$DECODED_1_MMS_ADDRESS" "$DECODED_1_MMS_SENDER" "$DECODED_1_MMS_TITLE" >> /tmp/smsd-mms.log
fi
π Processing message text in Python
the following script (if used as a RunOnReceive handler) written in Python will concatenate all text from a received message:
#!/usr/bin/env python
import os
numparts = int(os.environ["DECODED_PARTS"])
text = ""
# Are there any decoded parts?
if numparts == 0:
text = os.environ["SMS_1_TEXT"]
# Get all text parts
else:
for i in range(1, numparts + 1):
varname = "DECODED_%d_TEXT" % i
if varname in os.environ:
text = text + os.environ[varname]
# Do something with the text
print("Number {} have sent text: {}".format(os.environ["SMS_1_NUMBER"], text))
π Author π
Michal ΔihaΕ <michal@cihar.com> β the legend themselves π
π Copyright π
2009-2015, Michal ΔihaΕ <michal@cihar.com>
and that's the page, bestie! π«Ά this whole thing lives in the 1.45.0 era, dated Sep 16, 2026. go forth and let your hooks slay π
β¨πΈ
π¦ where this page comes from
- arch rolling: gammu 1.45.0-1 Β· GPL-2.0-or-later
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash-1017 on : a language model's rewrite of the original, under its terms