Send an SMS message to a cellphone with Kontact/kaddressbook

I have spent a little time trying to find out the best way to send an SMS message to a cellphone using Linux. There is a smattering of information scattered around, but I haven’t found a complete explanation in any one place and the documentation of the SMS interface in kaddressbook seems to be a little lacking so I have attempted to document something here in the hopes it may be useful to people interested in the topic.

There seems to be two types of SMS messages. The “slow” type uses an “email to SMS” gateway of the network provider (most free SMS web messaging services use this method). Slow type SMS messages may not always work if, for example, the network provider has not activated this type of gateway, or the cellphone is on an MVNO (“mobile virtual network operator” ie a cellular service provider like Virgin Mobile USA who resells calling minutes from one or more real carriers). The “fast” type uses another type of gateway for which a charge is normally incurred by the sender of the message. Skype uses the fast type SMS messaging and charges a fee for each message sent (Eur 0.09/message within North America for example). In the current Windows version Skype has the ability to send an SMS message directly but in the Linux version of Skype the SMS service is not available in the Skype program itself. However, there is a Skype API which can access these features of Skype. Skype4Py is a Python wrapper for the Skype API and can be found here:

https://developer.skype.com/wiki/Skype4Py

In addition, there is a set of Python command line tools which use Skype4Py called “Skype Tools 0.11”. Skype Tools 0.11 can be found here:

Vincent Oberle » Command-line tools for Skype

The particular tool we are interested in is the Python script send_sms.py. After installing Python, Skype4Py and Skype Tools, and with Skype for Linux running in the background you will be in a position to send an SMS message from the command line using send_sms.py. The first time you try to use send_sms.py you will need to give permission to Skype to allow Skype4Py and “sms_sender” (the “friendly name” of send_sms.py) to access Skype. Check under:

S -> Options -> Public API -> Allowed Programs

I am indebted to Happy coding » Blog Archive » How to send SMS in Linux using Skype for documenting the first two pieces of the Linux to SMS puzzle for me.

The final step is to integrate send_sms.py into the SMS message feature of kontact/kaddressbook. For the telephone number of the cellphone, under “Mobile” enter the telephone address in the form required by Skype. For example if the telephone number is 123-456-7890 enter +11234567890 as the “Mobile” number. The “Mobile” tag shows “(SMS)” at the end of the telephone number, as in:

Mobile: +11234567890 (SMS)

Clicking on “(SMS)” (do not click on the telephone number) throws up a small dialog window with the title “Send SMS - Kontact” in which the text message can be entered and also shows the character count of the message being prepared. For the purpose of the script below, if a newline is required in the message enter "
" as in: “This is line 1
This is line 2” Do not enter control characters such as newlines directly and just let the message string wrap inside the dialog box.

After entering the text message in the dialog press the “Send” button and the message will be sent. Skype must be running in the background of course.

Steps to prepare kaddressbook for message sending:

Pressing the “Send” button in the “Send SMS - Kontact” window creates a small text file containing the text with the filename mp\kde-[username]\kontact[6 char string].tmp (in KDE3). The variable “%F” created by kaddressbook contains this file name. The variable “%N” contains the telephone number string. So we have the information required for an SMS message but the text is in a file instead of the last part of the input string as required by send_sms.py. The bash script below which I have called “sendSMS.sh” will prepare and send the correct input string to send_sms.py. Prepare kaddressbook to use sendSMS.sh by making sendSMS.sh executable and placing it somewhere in your $PATH such as /home/[username]/bin/. Finally, set up a kaddressbook script hook as follows:

 Kontact -> Settings -> Configure Address Book... ->
 Script-Hooks -> SMS Text:
 enter the following:   sendSMS.sh %N %F

Here is my bash script sendSMS.sh:

#!/bin/bash

prepare string for execution by send_sms.py

SKYPE FOR LINUX MUST BE RUNNING

$1 is %N = telephone number in form required by Skype

$2 is %F = file name containing text of message

this is automatically created by kaddressbook

after closing the SMS message window

actual file is named (in KDE3)

/tmp/kde-[username]/kontact[6 char string].tmp

Text must be a single line string as the script

as written only captures the first line of text.

Line breaks in text message may be embedded with \

eg. This is line 1.\

This is line 2.

enter into Kontact->Settings->

Configure Address Book…->

Script-Hooks->SMS Text: sendSMS.sh %N %F

exec 6<&0
exec < $2
read line1
string=$1" "$line1
exec 0<&6 6<&-
send_sms.py $string

A more elegant way to do this would be to simply modify the python script send_sms.py to use the file name and use the revised Python script as our kaddressbook hook, but as I am unfamiliar with Python programming I devised the little bash script. The script just redirects the contents of the first line of the file containing the SMS message into the bash variable “line1” and concatenates into “string” the variable with a prepended telephone number and space which is then used as the input to send_sms.py which together with Skype4Py access the Skype API and send the SMS.

I don’t use skype. But prefer this: Voipcheap | Free voip calls are one step away!

I have a SIP gateway connected to my router and a normal phone plugs in to the gateway. That’s for calls. Text are done via the web interface. You login to your account and all your stored numbers are there. Cost is free or 2cents once you start using your credit after 90days.

Its so easy and I save a whole packet.

My last landline phone calls bill was 2 pence UK.

Hi
Nice howto :slight_smile:

Our cellphone provider here (cellularsouth) allows you to receive email
sms’s it’s less than a minute every time I’ve done it as well as sms to
email.


Cheers Malcolm °¿° (Linux Counter #276890)
openSUSE 11.0 x86 Kernel 2.6.25.18-0.2-default
up 18:43, 3 users, load average: 0.17, 0.12, 0.17
GPU GeForce 6600 TE/6200 TE - Driver Version: 177.82

I should point out that in paragraph two of my original post I used Virgin Mobile US as an example of an MVNO which is true, but it does appear that Virgin Mobile has an email to SMS service so it isn’t an example where web-based SMS messaging would fail. It is also possible to set up kaddressbook with a kmail script hook to send to cellphones where the provider has implemented an email to SMS gateway because in that case you could just send an email to the cellphone email address eg [cell number]@vmobl.com.

I am not trying to get into the virtues of any particular cellphone provider but describe a method of SMS sending out of Linux and KDE which should “always” work. The other difference between “slow” and “fast” SMS messaging is that the slow method can be quite slow depending on the priority which the carrier gives to this service whereas the fast method “should” arrive in a couple of seconds.

Nice howto.

Nice discussion about several possibilities.

Thanks.

That service is way too unreliable, they change their rates way too often without notice (as mentioned in their ToS) and this company has a lot of different websites for the same service with different rates, for example:
voipsstunt.com
smsdiscount.com
voipraider.com
voipcheap.com

And there are plenty more! Just browse the rates to see which one is the cheapest but make sure to check back often.

If you prefer a cross-platform open source solution with SMS support: WengoPhone - appels gratuits et illimités dans le monde, chat, vidéo, voip

The following Python+DBus code will tell Konqueror to navigate to PlusGSM HTTP gateway and to fill the fields with your information. You have to press the “Submit” button yourself; otherwise the script would run afoul of the service agreement. This gateway is useful for sending SMS to PlusGSM numbers only. Since you are likely to need other SMS services, I share this script as sample code.

The developers of this particular HTTP gateway went to great lengths to make it as scrambled and inaccessible as possible. I expect that details of the gateway are subject to change without notification and the script will have to be updated. The easiest way to detect it is to inject the following script into the browser:


var l_c = document. body. getElementsByTagName ("INPUT"), 
an_ix = 0; for (; +an_ix < +l_c. length; ++an_ix) l_c. value = +an_ix

Do the same for every TEXTAREA and you are basically done, unless the developers are particularly malicious and use features unsupported by older browsers.

Note that this script does not support sites that require you to authenticate first, basically because the alert window keeps the user from operating the service. Any advice how to handle that case would be welcome. GNOME users are encouraged to rewrite this code to talk to Firefox, or whatever their favourite browser is.

All right, enough chatting, down to the meat:


#!/usr/bin/python
# -*- coding: utf-8 -*-

import sys
import locale
locale. setlocale (locale. LC_ALL, '')

def get_alert_text ():
  alert_texts = { 
None: 'Wait until the form displays…', 
'pl_PL': 'Počekai na vyśvietlenie formulařa…' }
  lang = locale. getlocale (locale. LC_MESSAGES) [0]
  if not lang in alert_texts:
    lang = None
  return alert_texts [lang]

import dbus

bus = dbus.SessionBus()
lp = bus. get_object ('org.kde.klauncher', '/KLauncher')
lx = dbus. Interface(lp, 'org.kde.KLauncher')
kql = lx. start_service_by_desktop_name ('Konqueror', 'http://www1.plus.pl/bsm/'], ], '', 0)
if kql [0] == 0:
  khp = bus. get_object (kql [01], '/KHTML/1/widget')
  print 'Connected to ', kql [01]
  khx = dbus. Interface (khp, 'org.kde.KHTMLPart')
  with open (sys. argv [02], 'r') as msg:
    khx. evalJS ('alert (\'%s\'); '
'document. getElementsByTagName (\'INPUT\') [011]. value = \'%s\';'
'document. getElementsByTagName (\'TEXTAREA\') [0]. value = \'%s\'' 
% (get_alert_text (), sys. argv [01], msg. read(). encode ('string_escape'))
)

exit ()