Dropbox Python API
February 20, 2016 6 Comments
Assume that you are building a data logger and need to send your data from your logger to you, one option that will not cost you money or much programming time is to send your data file to your Dropbox. Dropbox is a cloud storage service. It not only provides you free cloud storage, but also provides application programming interface so you can upload files via programs. This requires some minimal setup. Once set up, you can proceed to add the file upload feature to your code. I am using Python to do the job. It is quick and easy. Plus, you can port your code to any operating system, such as PC running windows, GNU/Linux, Mac OSX, or Raspberry Pi. I am assuming that you have Python 3.X.
There are two versions of Dropbox Python API, V1 and V2. V2 came out around the end of 2015 and only has minimal tutorial on Dropbox.com. Nevertheless, I will use V2. Installing the API is a snap:
On Windows:
Start a command prompt and enter:
pip install dropbox
On Raspberry Pi (Raspbian Jessie) or Debian PC
sudo pip3 install dropbox
If you still have Raspbian Wheezy, pip3 may tell you that there is a newer version of pip. Don’t attempt to upgrade your pip or pip3. It will break.
Here is a short Python script to upload and download files:
[code language=”python”]
import dropbox
file_name=’test_image.jpg’
dropbox_path=’/’
dbx=dropbox.Dropbox(‘Your access token’)
with open(file_name, ‘rb’) as f:
dbx.files_upload(f.read(),dropbox_path+file_name,mute=True) # The change from f to f.read() was made to comply with the late-2016 change in the API.
dbx.files_download_to_file(‘Copy of ‘+file_name,dropbox_path+file_name)
[/code]
This was easy. There are only three functions that I used, first an authentication, then upload, followed by download. Your access token is generated by Dropbox. This post has the details.
The function dropbox.Dropbox() returns an object. You can use this object to upload or download files and more.
The files_upload() function does the upload. You need to first open the file on your local computer with open(). I am assuming the file is stored in the same folder as your Python script. This returns a file handler f. Then pass f to the files_upload(). This is the first argument. The next argument is the path you want the file to be uploaded to dropbox. It has to start with ‘/’, then the file name (including additional path). You don’t have to preserve file name. The third argument is useful. When you sent mute to True, you won’t get notification for the file upload. If you are making a camera trap, you don’t want your PC flooded with Dropbox notifications just because a bunny decides to visit your backyard.
The files_download_to_file requires first a local computer name, then the Dropbox file name. Again you don’t have to preserve file name. It’s useful to first check if the file exists on your local computer and decide what to do (overwrite, or add prefix/postfix to new file).
This is it! How you use it is up to you.
If you are interested, you can explore the rest of the API, such as creating folders, moving files, listing folders, etc. by reading the documentation (alert: document is very dry)
https://www.dropbox.com/developers/documentation/python
In my next post, I will make a simple Raspberry Pi camera logger to activate only during several intervals of time of the day.
Can you give a V2 API example to keep a local pi folder in sync with a Dropbox folder so that the Dropbox folder is the master and Pi is the slave. i.e. I push an update to DropBox and then the next time the script runs on the Pi it will download any new changes.
That will probably involve some background program routinely checking the Dropbox server for changes to the files that the PI wants. I’ll think about it and write something up when I have more time to play with it. My recommendation would be to create a separate Dropbox account if you want to try and code this slave program, just in case… 🙂
Maybe obvious to those that are familiar with python (I am not), there is a small error in line 6. The correct is:
dbx.files_upload(f.read() , dropbox_path+file_name,mute=True)
And then it all works :-), thanks
Thanks for the comment. The change you made was actually the result of a late-2016 update by Dropbox API. I’ve made the update on the post. It’s not a Python syntax thing, but rather was changed by Dropbox. Instead of passing the file handle, Dropbox now wants the code to pass the entire content (f.read() reads all content of the file) to the call.
Are you sure it does not cost? All I can see in the Dropbox site is the fees for dbx platform, which is what allows you to use the api. And I don’t see any ‘free tier’.
Yeah, they charge you money if you exceed a certain number of clients but you can use it for development purposes for up to 100 clients for free. Now you can bump that to 500 for free as well. For more clients down the road, you can pay your way into more service. It’s perfect for developers to test out their ideas before committing to any amount of money. I’ve never paid dropbox for anything so nothing I discussed in the post could have been a paid feature 🙂