Python Bluetooth how to send a file to a phone

j.gooch picture j.gooch · Feb 16, 2017 · Viewed 12k times · Source

in my current project it is a requirement to send a file from a windows computer to an android device over bluetooth without anything on the phone other than it's standard state and of course a paired bluetooth connection. i've looked over pybluez and it seemed simple enough to send files between a client and server architecture (and in fact got it sending between my laptop and desktop rather quickly) but I cannot for the life of me find any way to get python to send a file from the computer to android once the connection is established; my attempts have been grabbing the bluetooth mac address like thing from the device like so

nearby_devices = bluetooth.discover_devices(
    duration=8, lookup_names=True, flush_cache=True, lookup_class=False)

and then later trying to send the files like so

port = 1
for addr, name in nearby_devices:
    bd_addr = addr
sock=bluetooth.BluetoothSocket( bluetooth.RFCOMM )
sock.connect((bd_addr, port))

sock.send("download-app")
sock.close()

Of course with the example script given by the pybluez documentation I can seamlessly send files between a client and a server but I am still stuck without a way to send a file to the selected android device (even if I specify it's address and know it's within range)

Answer

Peter Brittain picture Peter Brittain · Feb 24, 2017

You're most of the way there...

As you know, you need something to talk to at the other end of your Bluetooth connection. You just need to replace your custom server with a well-known service (generally one of these options).

In my case, my phone supports the "OBEX Object Push" service, so I just need to connect to that and use a suitable client to talk the right protocol. Fortunately, the combination of PyOBEX and PyBluez does the trick here!

The following code (quickly patched together from PyOBEX and PyBluez samples) runs on my Windows 10, Python 2.7 installation and creates a simple text file on the phone.

from bluetooth import *
from PyOBEX.client import Client
import sys

addr = sys.argv[1]
print("Searching for OBEX service on %s" % addr)

service_matches = find_service(name=b'OBEX Object Push\x00', address = addr )
if len(service_matches) == 0:
    print("Couldn't find the service.")
    sys.exit(0)

first_match = service_matches[0]
port = first_match["port"]
name = first_match["name"]
host = first_match["host"]

print("Connecting to \"%s\" on %s" % (name, host))
client = Client(host, port)
client.connect()
client.put("test.txt", "Hello world\n")
client.disconnect()

Looks like PyOBEX is a pretty minimal package, though, and isn't Python 3 compatible, so you may have a little porting to do if that's a requirement.