Fixed #25838 -- Added "python" as an interface to the shell command.

Deprecates the "--plain" option.
This commit is contained in:
Jon Dufresne 2015-12-13 11:33:39 -08:00 committed by Tim Graham
parent b10f66831b
commit f1628f6be1
4 changed files with 70 additions and 54 deletions

View File

@ -1,20 +1,23 @@
import os import os
import warnings
from django.core.management.base import BaseCommand from django.core.management.base import BaseCommand
from django.utils.deprecation import RemovedInDjango20Warning
class Command(BaseCommand): class Command(BaseCommand):
help = "Runs a Python interactive interpreter. Tries to use IPython or bpython, if one of them is available." help = "Runs a Python interactive interpreter. Tries to use IPython or bpython, if one of them is available."
requires_system_checks = False requires_system_checks = False
shells = ['ipython', 'bpython'] shells = ['ipython', 'bpython', 'python']
def add_arguments(self, parser): def add_arguments(self, parser):
parser.add_argument('--plain', action='store_true', dest='plain', parser.add_argument('--plain', action='store_true', dest='plain',
help='Tells Django to use plain Python, not IPython or bpython.') help='Tells Django to use plain Python, not IPython or bpython. '
'Deprecated, use the `-i python` or `--interface python` option instead.')
parser.add_argument('--no-startup', action='store_true', dest='no_startup', parser.add_argument('--no-startup', action='store_true', dest='no_startup',
help='When using plain Python, ignore the PYTHONSTARTUP environment variable and ~/.pythonrc.py script.') help='When using plain Python, ignore the PYTHONSTARTUP environment variable and ~/.pythonrc.py script.')
parser.add_argument('-i', '--interface', choices=self.shells, dest='interface', parser.add_argument('-i', '--interface', choices=self.shells, dest='interface',
help='Specify an interactive interpreter interface. Available options: "ipython" and "bpython"') help='Specify an interactive interpreter interface. Available options: "ipython", "bpython", and "python"')
def _ipython_pre_011(self): def _ipython_pre_011(self):
"""Start IPython pre-0.11""" """Start IPython pre-0.11"""
@ -34,7 +37,7 @@ class Command(BaseCommand):
from IPython import start_ipython from IPython import start_ipython
start_ipython(argv=[]) start_ipython(argv=[])
def ipython(self): def ipython(self, options):
"""Start any version of IPython""" """Start any version of IPython"""
for ip in (self._ipython, self._ipython_pre_100, self._ipython_pre_011): for ip in (self._ipython, self._ipython_pre_100, self._ipython_pre_011):
try: try:
@ -46,56 +49,55 @@ class Command(BaseCommand):
# no IPython, raise ImportError # no IPython, raise ImportError
raise ImportError("No IPython") raise ImportError("No IPython")
def bpython(self): def bpython(self, options):
import bpython import bpython
bpython.embed() bpython.embed()
def run_shell(self, shell=None): def python(self, options):
available_shells = [shell] if shell else self.shells import code
# Set up a dictionary to serve as the environment for the shell, so
# that tab completion works on objects that are imported at runtime.
imported_objects = {}
try: # Try activating rlcompleter, because it's handy.
import readline
except ImportError:
pass
else:
# We don't have to wrap the following import in a 'try', because
# we already know 'readline' was imported successfully.
import rlcompleter
readline.set_completer(rlcompleter.Completer(imported_objects).complete)
readline.parse_and_bind("tab:complete")
# We want to honor both $PYTHONSTARTUP and .pythonrc.py, so follow system
# conventions and get $PYTHONSTARTUP first then .pythonrc.py.
if not options['no_startup']:
for pythonrc in (os.environ.get("PYTHONSTARTUP"), '~/.pythonrc.py'):
if not pythonrc:
continue
pythonrc = os.path.expanduser(pythonrc)
if not os.path.isfile(pythonrc):
continue
try:
with open(pythonrc) as handle:
exec(compile(handle.read(), pythonrc, 'exec'), imported_objects)
except NameError:
pass
code.interact(local=imported_objects)
def handle(self, **options):
if options['plain']:
warnings.warn(
"The --plain option is deprecated in favor of the -i python or --interface python option.",
RemovedInDjango20Warning
)
options['interface'] = 'python'
available_shells = [options['interface']] if options['interface'] else self.shells
for shell in available_shells: for shell in available_shells:
try: try:
return getattr(self, shell)() return getattr(self, shell)(options)
except ImportError: except ImportError:
pass pass
raise ImportError raise ImportError("Couldn't load any of the specified interfaces.")
def handle(self, **options):
try:
if options['plain']:
# Don't bother loading IPython, because the user wants plain Python.
raise ImportError
self.run_shell(shell=options['interface'])
except ImportError:
import code
# Set up a dictionary to serve as the environment for the shell, so
# that tab completion works on objects that are imported at runtime.
# See ticket 5082.
imported_objects = {}
try: # Try activating rlcompleter, because it's handy.
import readline
except ImportError:
pass
else:
# We don't have to wrap the following import in a 'try', because
# we already know 'readline' was imported successfully.
import rlcompleter
readline.set_completer(rlcompleter.Completer(imported_objects).complete)
readline.parse_and_bind("tab:complete")
# We want to honor both $PYTHONSTARTUP and .pythonrc.py, so follow system
# conventions and get $PYTHONSTARTUP first then .pythonrc.py.
if not options['no_startup']:
for pythonrc in (os.environ.get("PYTHONSTARTUP"), '~/.pythonrc.py'):
if not pythonrc:
continue
pythonrc = os.path.expanduser(pythonrc)
if not os.path.isfile(pythonrc):
continue
try:
with open(pythonrc) as handle:
exec(compile(handle.read(), pythonrc, 'exec'), imported_objects)
except NameError:
pass
code.interact(local=imported_objects)

View File

@ -126,6 +126,8 @@ details on these changes.
* ``django.utils.functional.allow_lazy()`` will be removed. * ``django.utils.functional.allow_lazy()`` will be removed.
* The ``shell --plain`` option will be removed.
.. _deprecation-removed-in-1.10: .. _deprecation-removed-in-1.10:
1.10 1.10

View File

@ -933,9 +933,15 @@ Starts the Python interactive interpreter.
Django will use IPython_ or bpython_ if either is installed. If you have a Django will use IPython_ or bpython_ if either is installed. If you have a
rich shell installed but want to force use of the "plain" Python interpreter, rich shell installed but want to force use of the "plain" Python interpreter,
use the ``--plain`` option, like so:: use the ``-i python`` or ``--interface python`` option, like so::
django-admin shell --plain django-admin shell -i python
django-admin shell --interface python
.. deprecated:: 1.10
In older versions, use the ``--plain`` option. This is deprecated and will
be removed in Django 2.0.
If you would like to specify either IPython or bpython as your interpreter if If you would like to specify either IPython or bpython as your interpreter if
you have both installed you can specify an alternative interpreter interface you have both installed you can specify an alternative interpreter interface
@ -957,12 +963,12 @@ bpython::
.. _bpython: http://bpython-interpreter.org/ .. _bpython: http://bpython-interpreter.org/
When the "plain" Python interactive interpreter starts (be it because When the "plain" Python interactive interpreter starts (be it because
``--plain`` was specified or because no other interactive interface is ``--interface python`` was specified or because no other interactive interface
available) it reads the script pointed to by the :envvar:`PYTHONSTARTUP` is available) it reads the script pointed to by the :envvar:`PYTHONSTARTUP`
environment variable and the ``~/.pythonrc.py`` script. If you don't wish this environment variable and the ``~/.pythonrc.py`` script. If you don't wish this
behavior you can use the ``--no-startup`` option. e.g.:: behavior you can use the ``--no-startup`` option. e.g.::
django-admin shell --plain --no-startup django-admin shell --interface python --no-startup
showmigrations [<app_label> [<app_label>]] showmigrations [<app_label> [<app_label>]]
------------------------------------------ ------------------------------------------

View File

@ -212,6 +212,9 @@ Management Commands
* :djadmin:`makemigrations` now displays the path to the migration files that * :djadmin:`makemigrations` now displays the path to the migration files that
it generates. it generates.
* The :djadmin:`shell` ``--interface`` option now accepts ``python`` to force
use of the "plain" Python interpreter.
Migrations Migrations
^^^^^^^^^^ ^^^^^^^^^^
@ -432,6 +435,9 @@ Miscellaneous
:func:`~django.utils.functional.keep_lazy` function which can be used with a :func:`~django.utils.functional.keep_lazy` function which can be used with a
more natural decorator syntax. more natural decorator syntax.
* The ``shell --plain`` option is deprecated in favor of ``-i python`` or
``--interface python``.
.. _removed-features-1.10: .. _removed-features-1.10:
Features removed in 1.10 Features removed in 1.10