Skip to content

Instantly share code, notes, and snippets.

@Quotation
Forked from defrex/shell.py
Last active August 19, 2023 14:23
Show Gist options
  • Select an option

  • Save Quotation/909f87320b03b028d23c to your computer and use it in GitHub Desktop.

Select an option

Save Quotation/909f87320b03b028d23c to your computer and use it in GitHub Desktop.
Use ptpython for Django shell
from django.core.management.commands.shell import Command as ShellCommand
import os
class Command(ShellCommand):
shells = ShellCommand.shells.append('ptpython')
def ptpython(self):
try:
# old ptpython
from prompt_toolkit.contrib.repl import embed
except ImportError:
# new ptpython
from ptpython.repl import embed
history_filename = os.path.expanduser('~/.ptpython_history')
embed(globals(), locals(), vi_mode=False, history_filename=history_filename)
@yatmanov
Copy link

First of all thanks for the code, I've been using this for a long period of time. ptpython provides very convenient way of interactions with django apis. But unfortunately this does not work anymore, at least with Django version 2.2.6

For me ./manage.py shell -i ptpython command produces following traceback:

Traceback (most recent call last):
  ...
  File "C:\Users\yatmanov\AppData\Local\Programs\Python\Python37\lib\site-packages\django\core\management\__init__.py", line 381, in execute_from_command_line
    utility.execute()
  File "C:\Users\yatmanov\AppData\Local\Programs\Python\Python37\lib\site-packages\django\core\management\__init__.py", line 375, in execute
    self.fetch_command(subcommand).run_from_argv(self.argv)
  File "C:\Users\yatmanov\AppData\Local\Programs\Python\Python37\lib\site-packages\django\core\management\base.py", line 323, in run_from_argv
    self.execute(*args, **cmd_options)
  File "C:\Users\yatmanov\AppData\Local\Programs\Python\Python37\lib\site-packages\django\core\management\base.py", line 364, in execute
    output = self.handle(*args, **options)
  File "C:\Users\yatmanov\AppData\Local\Programs\Python\Python37\lib\site-packages\django\core\management\commands\shell.py", line 99, in handle
    return getattr(self, shell)(options)
TypeError: ptpython() takes 1 positional argument but 2 were given

So I searched for other solutions and found it on ptpython project's github page: https://github.com/prompt-toolkit/ptpython#django-support

All you need to do is install django-extensions alongside with ptpython, and add it to INSTALLED_APPS. After that you can prompt ptpython by next command:
python manage.py shell_plus

@michaelhays
Copy link

michaelhays commented Nov 13, 2019

If you get:

TypeError: ptpython() takes 1 positional argument but 2 were given

try changing

def ptpython(self):

to

def ptpython(self, options):

Here's my full management/commands/shell.py file:

import os

from django.core.management.commands.shell import Command
from ptpython.repl import embed


def ptpython(self, options):
    history_filename = os.path.expanduser("~/.ptpython_history")
    embed(globals(), locals(), vi_mode=False, history_filename=history_filename)


Command.ptpython = ptpython
Command.shells.insert(0, "ptpython")

@namper
Copy link

namper commented Sep 10, 2022

Append is incorrect should be ShellCommand.shells + ['ptpython']

Full version:

from django.core.management.commands.shell import Command as ShellCommand
import os


class Command(ShellCommand):
    shells = ShellCommand.shells + ['ptpython']

    def ptpython(self, options):
        from ptpython.repl import embed

        history_filename = os.path.expanduser('~/.ptpython_history')
        embed(globals(), locals(), vi_mode=False, history_filename=history_filename)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment