pyftpdlib is a high-level library to easily write asynchronous portable FTP servers with Python.
Yes. pyftpdlib is a fully working FTP server implementation that can be run "as is". For example, (after having installed a Python interpreter) you could run an anonymous ftp server from cmd-line by running:
python -m pyftpdlib.ftpserver
Customizing ftpd for basic tasks like adding users or deciding where log file should be placed is mostly simply editing variables. This is basically like learning how to edit a common unix ftpd.conf file and doesn't really require Python knowledge. Customizing ftpd more deeply requires a python script which imports pyftpdlib to be written separately. An example about how this could be done are the scripts contained in the demo directory.
http://code.google.com/p/pyftpdlib/ is the primary source for all information about the project including Install instructions, Tutorial, RFCs Compliance paper, Wikis and the Bug Tracker.
There are a number of mailing lists for pyftpdlib:
Name | Web Interface | Description | |
pyftpdlib | pyftpdlib@googlegroups.com | topics | This is intended for end user support. |
pyftpdlib-commit | pyftpdlib-commits@googlegroups.com | topics | This list receives all change notifications for code in the Subversion repository. Unless you're a pyftpdlib developer you will probably not be interested in it. |
pyftpdlib-issues | pyftpdlib-issues@googlegroups.com | topics | This list receives all change notifications from the Bug Tracker. Unless you are involved into pyftpdlib development you will probably not find this useful. |
Bug reports should be made via Google Code Issue Tracker. Patches should be attached to the appropriate bug and not mailed directly to the mailing lists or any given team member.
If you are not new to Python you probably don't need that, otherwise follow the instructions.
Python 2.3 and higher.
Python 2.6 which provides a faster and cleaner asyncore implementation.
pyftpdlib should work on any platform where select() or poll() system calls are available and on any Python implementation which refers to cPython 2.3 or superior (e.g cPython 2.6 or PythonCE 2.5). The development team has mainly tested it under various Linux, Windows, OS X and FreeBSD systems. For FreeBSD is also available a pre-compiled package maintained by Li-Wen Hsu <lwhsu@freebsd.org>. Other Python implementation like PythonCE are known to work with pyftpdlib and every new version is usually tested against it. pyftpdlib currently does not work on Jython since the latest Jython release refers to CPython 2.2.x serie. The best way to know whether pyftpdlib works on your platform is installing it and running its test suite.
class MyHandler(ftpserver.FTPHandler):
def on_file_received(self, file):
"""Called every time a file has been received"""
def blocking_task():
time.sleep(5)
self.sleeping = False
self.sleeping = True
threading.Thread(target=blocking_task).start()
Just modify banner attribute of FTPHandler class.
Yes. Starting from version 0.5.2 ftpserver.py provides a new class called ThrottledDTPHandler. You can set speed limits by modifying read_limit and write_limit class attributes as it is shown in throttled_ftpd.py demo script.
FXP is part of the name of a popular Windows FTP client: http://www.flashfxp.com. This client has made the name "FXP" commonly used as a synonym for site-to-site FTP transfers, for transferring a file between two remote FTP servers without the transfer going through the client's host. Sometimes "FXP" is referred to as a protocol; in fact, it is not. The site-to-site transfer capability was deliberately designed into RFC-959. More info can be found here: http://www.proftpd.org/docs/howto/FXP.html.
Yes. It is disabled by default for security reasons (see RFC-2257 and FTP bounce attack description) but in case you want to enable it just set to True the permit_foreign_addresses attribute of FTPHandler class.
Globbing is a common Unix shell mechanism for expanding wildcard patterns to match multiple filenames. When an argument is provided to the STAT command, ftpd should return directory listing over the command channel. RFC-959 does not explicitly mention globbing; this means that FTP servers are not required to support globbing in order to be compliant. However, many FTP servers do support globbing as a measure of convenience for FTP clients and users. In order to search for and match the given globbing expression, the code has to search (possibly) many directories, examine each contained filename, and build a list of matching files in memory. Since this operation can be quite intensive, both CPU- and memory-wise, pyftpdlib does not support globbing.
Properly handling the SIZE command when TYPE ASCII is used would require to scan the entire file to perform the ASCII translation logic (file.read().replace(os.linesep, '\r\n')) and then calculating the len of such data which may be different than the actual size of the file on the server. Considering that calculating such result could be very resource-intensive it could be easy for a malicious client to try a DoS attack, thus pyftpdlib rejects SIZE when the current TYPE is ASCII. However, clients in general should not be resuming downloads in ASCII mode. Resuming downloads in binary mode is the recommended way as specified in RFC-3659.
Starting from version 0.4.0 pyftpdlib supports IPv6 (RFC-2428). If you use IPv6 and want your FTP daemon to do so just pass a valid IPv6 address to the FTPServer class constructor. Example:
>>> from pyftpdlib import ftpserver
>>> address = ("::1", 21) # listen on localhost, port 21
>>> ftpd = ftpserver.FTPServer(address, ftpserver.FTPHandler)
>>> ftpd.serve_forever()
Serving FTP on ::1:21
Yes. By using the proper system dependent authorizer pyftpdlib can look into the system account database to authenticate users. Starting from version 0.4.0 the DummyAuthorizer class provides two new methods: impersonate_user() and terminate_impersonation(). System dependent authorizers subclassing the dummy authorizer can assume the id of real users by overriding them as necessary. Every time the FTP server is going to access the filesystem (e.g. for creating or renaming a file) it will temporarily impersonate the currently logged on user, execute the filesystem call and then switch back to the user who originally started the server. Example UNIX and Windows FTP servers contained in the demo directory implement both real user impersonation and authentication against the system users database.
The standard code base does not offer any "official" FTPS support yet but starting from version 0.5.1 the demo directory contains a script which implements a simple FTPS daemon supporting both TLS and SSL protocols and AUTH, PBSZ and PROT commands as defined in RFC-4217.