1619

What is the Python 3 equivalent of python -m SimpleHTTPServer?

Adexe Rivera
  • 414
  • 7
  • 12
ryanbraganza
  • 16,863
  • 3
  • 17
  • 24

7 Answers7

2272

From the docs:

The SimpleHTTPServer module has been merged into http.server in Python 3.0. The 2to3 tool will automatically adapt imports when converting your sources to 3.0.

So, your command is python -m http.server, or depending on your installation, it can be:

python3 -m http.server
Petr Viktorin
  • 65,510
  • 9
  • 81
  • 81
  • 99
    In Python 3.3, the replacement for `python -m CGIHTTPServer` is `python3 -m http.server --cgi`. – bseibold Feb 21 '13 at 15:53
  • 1
    Can you bind a different IP/Port with that command? How would I do that? – CMCDragonkai Jun 04 '14 at 08:24
  • 27
    Sure, just tack it on the end of the command line. Read `python3 -m http.server --help` for all the args & options. – Petr Viktorin Jun 04 '14 at 18:51
  • 33
    `python -m http.server` worked for me. I had to remove the `3` – nu everest Jul 09 '15 at 20:59
  • 16
    @nueverest It depends on how your Python installation is 'named'. Usually Python2 is available as `python` and Python3 as `python3` but some prefer to install Python3 simply as `python`. – Mast Jul 14 '15 at 08:02
  • 6
    AFAIK, on Windows, it'll install as just `python` by default. But, the question is for `python3` :) – Petr Viktorin Jul 14 '15 at 20:10
  • @CMCDragonkai `python -m http.server --bind 192.168.1.14 8000 >>> Serving HTTP on 192.168.1.14 port 8000 ... ` – Zombro Jul 08 '16 at 20:41
  • python3 is now named 'python' for homebrew-managed installs on OSX. – justinpitts Mar 04 '18 at 14:11
  • @CMCDragonkai more examples at the end of this section: https://docs.python.org/3/library/http.server.html#http.server.SimpleHTTPRequestHandler – AdamKalisz Aug 22 '18 at 08:35
  • is it possible to call this in a py2x and py3x compatible way? I tried using the six library but it doesnt seem to work with: 'python -m six.moves.SimpleHTTPServer' – fersarr Oct 11 '18 at 13:14
  • just installed python 3.7.1 on windows, neither `python` nor `python3` worked, just `py` worked! – Paramvir Singh Karwal Nov 04 '18 at 17:09
  • 1
    @ParamvirSinghKarwal `py` is a wrapper on windows because Linux has a feature where if a script is marked executable and starts with a "shebang" (as in `#! /bin/python3`) executing it as a command (as in `./yourscript.py`) will run it with that program so you can chose which version to run your script under, unless someone manually does `python2 yourscript.py`. Windows uses just the files extension to decide which program to use so `py` is set to open .py files and looks for a shebang and then executes it under the correct python version. – SilentVoid Feb 11 '19 at 18:53
  • And on Arch I have `python` (Python 3), `python2`, `python2.7`, `python3`, and `python3.7`. If a had 2.6 for example, I'd also have a `python2.6`. – SilentVoid Feb 11 '19 at 18:53
  • another big fan of the " . " where people don't want one for copy & paste reasons. Must have been put there on purpose. <--- HERE a dot / full stop does belong, since there is no bash code involved, you see. – dotbit Jul 17 '19 at 16:32
  • @dotbit: That was an unfortunate result of an edit which turned an inline code example (like the `python -m http.server`) into a paragraph that had only code in it – but left the trailing comma. I've now turned it into a real code block. Please feel free to edit (or suggest edits) yourself when you see a mistake. Or just alert others if you see something that can be improved. There's no need for negativity :) – Petr Viktorin Jul 19 '19 at 07:48
  • @PetrViktorin what is the default `--bind` if I don't specify it? I looked into the docs but I cannot find it. – Kuzeko Mar 13 '20 at 08:40
  • 1
    @Kuzeko, the default is to listen on all interfaces (`''`). – Petr Viktorin Mar 16 '20 at 10:05
359

The equivalent is:

python3 -m http.server
Greg Hewgill
  • 951,095
  • 183
  • 1,149
  • 1,285
  • 79
    And `python3 -m http.server 8080` if You need to bind to a port. Read more at the end of the section: https://docs.python.org/3/library/http.server.html#http.server.SimpleHTTPRequestHandler – AdamKalisz Aug 22 '18 at 08:36
  • 5
    By default, it will bind to port 8000. See `python3 -m http.server --help` for details. – stephenwade Mar 20 '19 at 21:24
162

Using 2to3 utility.

$ cat try.py
import SimpleHTTPServer

$ 2to3 try.py
RefactoringTool: Skipping implicit fixer: buffer
RefactoringTool: Skipping implicit fixer: idioms
RefactoringTool: Skipping implicit fixer: set_literal
RefactoringTool: Skipping implicit fixer: ws_comma
RefactoringTool: Refactored try.py
--- try.py  (original)
+++ try.py  (refactored)
@@ -1 +1 @@
-import SimpleHTTPServer
+import http.server
RefactoringTool: Files that need to be modified:
RefactoringTool: try.py

Like many *nix utils, 2to3 accepts stdin if the argument passed is -. Therefore, you can test without creating any files like so:

$ 2to3 - <<< "import SimpleHTTPServer"
Bruno Bronosky
  • 66,273
  • 12
  • 162
  • 149
shantanoo
  • 3,617
  • 1
  • 24
  • 37
122

In addition to Petr's answer, if you want to bind to a specific interface instead of all the interfaces you can use -b or --bind flag.

python -m http.server 8000 --bind 127.0.0.1

The above snippet should do the trick. 8000 is the port number. 80 is used as the standard port for HTTP communications.

simhumileco
  • 31,877
  • 16
  • 137
  • 115
Eswar Yaganti
  • 2,536
  • 1
  • 20
  • 22
39

As everyone has mentioned http.server module is equivalent to python -m SimpleHTTPServer.
But as a warning from https://docs.python.org/3/library/http.server.html#module-http.server

Warning: http.server is not recommended for production. It only implements basic security checks.

Usage

http.server can also be invoked directly using the -m switch of the interpreter.

python -m http.server

The above command will run a server by default on port number 8000. You can also give the port number explicitly while running the server

python -m http.server 9000

The above command will run an HTTP server on port 9000 instead of 8000.

By default, server binds itself to all interfaces. The option -b/--bind specifies a specific address to which it should bind. Both IPv4 and IPv6 addresses are supported. For example, the following command causes the server to bind to localhost only:

python -m http.server 8000 --bind 127.0.0.1

or

python -m http.server 8000 -b 127.0.0.1

Python 3.8 version also supports IPv6 in the bind argument.

Directory Binding

By default, server uses the current directory. The option -d/--directory specifies a directory to which it should serve the files. For example, the following command uses a specific directory:

python -m http.server --directory /tmp/

Directory binding is introduced in python 3.7

Anand Tripathi
  • 14,556
  • 1
  • 47
  • 52
  • Everyone mentions "Warning: http.server is not recommended for production. It only implements basic security checks." but do you have any suggestions for easy to use file servers as alternatives. I have a docker app and I would like to run something like this server in a separate container behind nginx. Any suggestions? – Lucas Rahn Nov 10 '21 at 01:12
11

In one of my projects I run tests against Python 2 and 3. For that I wrote a small script which starts a local server independently:

$ python -m $(python -c 'import sys; print("http.server" if sys.version_info[:2] > (2,7) else "SimpleHTTPServer")')
Serving HTTP on 0.0.0.0 port 8000 ...

As an alias:

$ alias serve="python -m $(python -c 'import sys; print("http.server" if sys.version_info[:2] > (2,7) else "SimpleHTTPServer")')"
$ serve
Serving HTTP on 0.0.0.0 port 8000 ...

Please note that I control my Python version via conda environments, because of that I can use python instead of python3 for using Python 3.

Darius
  • 10,762
  • 2
  • 29
  • 50
10

Just wanted to add what worked for me: python3 -m http.server 8000 (you can use any port number here except the ones which are currently in use)

benson23
  • 16,369
  • 9
  • 19
  • 38
Shivam Papat
  • 457
  • 4
  • 14