How can I drop all tables from a database using manage.py and command line? Is there any way to do that executing manage.py with appropriate parameters so I can execute it from a .NET application?
20 Answers
As far as I know there is no management command to drop all tables. If you don't mind hacking Python you can write your own custom command to do that. You may find the sqlclear
option interesting. Documentation says that ./manage.py sqlclear
Prints the DROP TABLE SQL statements for the given app name(s).
Update: Shamelessly appropriating @Mike DeSimone's comment below this answer to give a complete answer.
./manage.py sqlclear | ./manage.py dbshell
As of django 1.9 it's now ./manage.py sqlflush

- 8,453
- 9
- 51
- 74

- 72,339
- 21
- 134
- 141
-
sqlclear "prints the drop statements" but how to execute them in single command line call – kmalmur Aug 05 '10 at 12:28
-
3you need the app name like: `./manage.py sqlclear myAppName | ./manage.py dbshell` – Montaro Jul 11 '15 at 02:32
-
4This doesn't work at all. sqlclear needs an app name. I'm on Django 1.8 – Jonathan Hartley Oct 12 '15 at 12:37
-
1Just be aware that sqlflush doesn't drop the tables, it truncates them. Also this operation probably won't work on your postgresql DB unless you add CASCADE keyword at the end of the truncate command generated by sqlflush. – user3748764 Jan 20 '19 at 13:35
-
1No `./manage.py sqlclear`, for me it was `sqlflush` – smac89 Aug 13 '21 at 05:34
There's no native Django management command to drop all tables. Both sqlclear
and reset
require an app name.
However, you can install Django Extensions which gives you manage.py reset_db
, which does exactly what you want (and gives you access to many more useful management commands).

- 10,056
- 3
- 28
- 32
-
5
-
1This worked for me, while none of the higher ranked answers did. – Jonathan Hartley Oct 12 '15 at 12:42
-
4@AnujGupta also often `manage.py reset_db` needs flag ` -c, --close-sessions` to close database connections before dropping database (PostgreSQL only) – Valery Ramusik Jul 18 '19 at 08:38
-
It is giving me Access denied for user '**MYUSERNAME**'@'localhost' (using password: NO) – levio_sa Apr 13 '21 at 14:05
-
1
-
If you're using the South package to handle database migrations (highly recommended), then you could just use the ./manage.py migrate appname zero
command.
Otherwise, I'd recommend the ./manage.py dbshell
command, piping in SQL commands on standard input.

- 41,631
- 10
- 72
- 96
-
+1. Any non-trivial Django project should use South. And once you use South then migrating to Zero is a nice idiomatic way of dropping all tables. – Manoj Govindan Jan 29 '13 at 10:08
-
Even trivial Django projects should consider South. Just to get people used to migrating databases, and so they don't learn bad habits like trying to dump, hack, and reload data by hand, or using the fixtures mechanism to migrate data. – Mike DeSimone Jan 29 '13 at 17:16
-
I do use South, but I don't bother writing reverse migrations for every migration: not least data migrations. And I wouldn't do that just so I can use the zero option. Certainly a good way of testing that you /can/ reverse right back to zero, if that's important to you. Dropping all the tables seems reasonable to me. – tobych Oct 16 '14 at 18:09
-
-
Well, this question is ancient, South got subsumed into Django around 1.7, and I’ve used commands to migrate to zero with dozens of apps. `reset_db` (above) is my preferred tool for blowing everything away, but I’ve used migrate to get back to zero too. Django is pretty good with catching cross-app dependencies when creating migrations, so rolling something like `auth` back to zero gets almost everything. – Mike DeSimone Nov 25 '21 at 20:55
python manage.py migrate <app> zero
sqlclear
was removed from 1.9.
Release notes mention that it is due to the introduction of migrations: https://docs.djangoproject.com/en/1.9/releases/1.9/
Unfortunately I could not find a method that works on all apps at once, nor a built-in way to list all installed apps from the admin: How to list all installed apps with manage.py in Django?

- 1
- 1

- 347,512
- 102
- 1,199
- 985
It is better to use ./manage.py sqlflush | ./manage.py dbshell
because sqlclear requires app to flush.

- 4,718
- 3
- 16
- 14
simple(?) way to do it from python (on mysql):
from django.db import connection
cursor = connection.cursor()
cursor.execute('show tables;')
parts = ('DROP TABLE IF EXISTS %s;' % table for (table,) in cursor.fetchall())
sql = 'SET FOREIGN_KEY_CHECKS = 0;\n' + '\n'.join(parts) + 'SET FOREIGN_KEY_CHECKS = 1;\n'
connection.cursor().execute(sql)

- 101
- 1
- 2
If you want to completely wipe the database and resync it in the same go you need something like the following. I also combine adding test data in this command:
#!/usr/bin/env python
import os
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "main.settings") # Replace with your app name.
from django.db import connection
from django.core.management import call_command
from django.conf import settings
# If you're using postgres you can't use django's sql stuff for some reason that I
# can't remember. It has to do with that autocommit thing I think.
# import psychodb2 as db
def recreateDb():
print("Wiping database")
dbinfo = settings.DATABASES['default']
# Postgres version
#conn = db.connect(host=dbinfo['HOST'], user=dbinfo['USER'],
# password=dbinfo['PASSWORD'], port=int(dbinfo['PORT'] or 5432))
#conn.autocommit = True
#cursor = conn.cursor()
#cursor.execute("DROP DATABASE " + dbinfo['NAME'])
#cursor.execute("CREATE DATABASE " + dbinfo['NAME'] + " WITH ENCODING 'UTF8'") # Default is UTF8, but can be changed so lets be sure.
# Mysql version:
print("Dropping and creating database " + dbinfo['NAME'])
cursor = connection.cursor()
cursor.execute("DROP DATABASE " + dbinfo["NAME"] + "; CREATE DATABASE " + dbinfo["NAME"] + "; USE " + dbinfo["NAME"] + ";")
print("Done")
if __name__ == "__main__":
recreateDb();
print("Syncing DB")
call_command('syncdb', interactive=False)
print("Adding test data")
addTestData() # ...
It would be nice to be able to do cursor.execute(call_command('sqlclear', 'main'))
but call_command
prints the SQL to stdout rather than returning it as a string, and I can't work out the sql_delete
code...

- 22,701
- 8
- 49
- 54

- 88,195
- 71
- 364
- 509
-
Nice the `USE DATABASE` I recommand you to create a django-recreate-db package with a management command which will auto switch based on the settings to switch between SQLite3 et PostGresql. – Natim Oct 10 '12 at 15:20
Here's a shell script I ended up piecing together to deal with this issue. Hope it saves someone some time.
#!/bin/sh
drop() {
echo "Droping all tables prefixed with $1_."
echo
echo "show tables" | ./manage.py dbshell |
egrep "^$1_" | xargs -I "@@" echo "DROP TABLE @@;" |
./manage.py dbshell
echo "Tables dropped."
echo
}
cancel() {
echo "Cancelling Table Drop."
echo
}
if [ -z "$1" ]; then
echo "Please specify a table prefix to drop."
else
echo "Drop all tables with $1_ prefix?"
select choice in drop cancel;do
$choice $1
break
done
fi

- 423
- 6
- 14
Here's an example Makefile to do some nice things with multiple settings files:
test:
python manage.py test --settings=my_project.test
db_drop:
echo 'DROP DATABASE my_project_development;' | ./manage.py dbshell
echo 'DROP DATABASE my_project_test;' | ./manage.py dbshell
db_create:
echo 'CREATE DATABASE my_project_development;' | ./manage.py dbshell
echo 'CREATE DATABASE my_project_test;' | ./manage.py dbshell
db_migrate:
python manage.py migrate --settings=my_project.base
python manage.py migrate --settings=my_project.test
db_reset: db_drop db_create db_migrate
.PHONY: test db_drop db_create db_migrate db_reset
Then you can do things like:
$ make db_reset

- 4,386
- 37
- 48
If you are using psql and have django-more 2.0.0 installed, you can do
manage.py reset_schema

- 12,622
- 6
- 51
- 57
The command ./manage.py sqlclear
or ./manage.py sqlflush
seems to clear the table and not delete them, however if you want to delete the complete database try this : manage.py flush
.
Warning: this will delete your database completely and you will lose all your data, so if that not important go ahead and try it.

- 520
- 1
- 7
- 15
-
3No, this is incorrect. flush and sqlflush is the same, it removes all data, but doesnt drop tables. sqlflush displays the sql, but does not execute, flush executes it without displaying it. – Moulde Jan 08 '18 at 17:03
This answer is for postgresql DB:
Run: echo 'drop owned by some_user' | ./manage.py dbshell
NOTE: some_user is the name of the user you use to access the database, see settings.py file:
default_database = {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': 'somedbname',
'USER': 'some_user',
'PASSWORD': 'somepass',
'HOST': 'postgresql',
'PORT': '',
}

- 5,041
- 3
- 34
- 30
I would recommend you to install django-extensions and use python manage.py reset_db
command. It does exactly what you want.

- 91
- 3
Using Python to make a flushproject command, you use :
from django.db import connection
cursor = connection.cursor()
cursor.execute(“DROP DATABASE %s;”, [connection.settings_dict['NAME']])
cursor.execute(“CREATE DATABASE %s;”, [connection.settings_dict['NAME']])

- 17,274
- 23
- 92
- 150
-
My question, is how to perform this if the database doesn't already exists ? – Natim Dec 13 '11 at 16:02
-
Sadly any further actions in the same script (e.g. syncdb) result in "No database selected" errors. – Timmmm Oct 08 '12 at 13:10
-
It did a command `flushdb` and after I launch another command. if you need it in another script, you might use `call_command` – Natim Oct 09 '12 at 12:55
-
I don't follow. I am already using `call_command`. You're saying I should do `call_command("flushdb")` before `call_command("syncdb")`? – Timmmm Oct 09 '12 at 13:32
-
Doesn't work. Same error. The error is "No database selected" so you can't execute *any* SQL. Found the solution: See my other answer. – Timmmm Oct 10 '12 at 11:14
Here's a south migration version of @peter-g's answer.
I often fiddle with raw sql, so this comes in handy as 0001_initial.py for any befuddled apps. It will only work on DBs that support SHOW TABLES
(like mysql). Substitute something like SELECT table_name FROM information_schema.tables WHERE table_schema = 'public';
if you use PostgreSQL. Also, I often do this exact same thing for both the forwards
and backwards
migrations.
from south.db import db
from south.v2 import SchemaMigration
from django.db.utils import DatabaseError
from os import path
from logging import getLogger
logger = getLogger(__name__)
class Migration(SchemaMigration):
def forwards(self, orm):
app_name = path.basename(path.split(path.split(path.abspath(__file__))[0])[0])
table_tuples = db.execute(r"SHOW TABLES;")
for tt in table_tuples:
table = tt[0]
if not table.startswith(app_name + '_'):
continue
try:
logger.warn('Deleting db table %s ...' % table)
db.delete_table(table)
except DatabaseError:
from traceback import format_exc
logger.error("Error running %s: \n %s" % (repr(self.forwards), format_exc()))
Coworker/cocoders would kill me if they knew I did this, though.

- 18,473
- 10
- 83
- 106
There's an even simpler answer if you want to delete ALL your tables. You just go to your folder containing the database (which may be called mydatabase.db) and right-click the .db file and push "delete." Old fashioned way, sure-fire to work.

- 9,146
- 10
- 55
- 88
Drops all tables and recreates them:
python manage.py sqlclear app1 app2 appN | sed -n "2,$p" | sed -n "$ !p" | sed "s/";/" CASCADE;/" | sed -e "1s/^/BEGIN;/" -e "$s/$/COMMIT;/" | python manage.py dbshell
python manage.py syncdb
Explanation:
manage.py sqlclear
- "prints the DROP TABLE SQL statements for the given app name(s)"
sed -n "2,$p"
- grabs all lines except first line
sed -n "$ !p"
- grabs all lines except last line
sed "s/";/" CASCADE;/"
- replaces all semicolons (;) with (CASCADE;)
sed -e "1s/^/BEGIN;/" -e "$s/$/COMMIT;/"
- inserts (BEGIN;) as first text, inserts (COMMIT;) as last text
manage.py dbshell
- "Runs the command-line client for the database engine specified in your ENGINE setting, with the connection parameters specified in your USER, PASSWORD, etc., settings"
manage.py syncdb
- "Creates the database tables for all apps in INSTALLED_APPS whose tables have not already been created"
Dependencies:
- sed, to use on Windows, I installed UnxUtils: (Download) (Installation Instructions)
Credits:
@Manoj Govindan and @Mike DeSimone for sqlclear piped to dbshell
@jpic for 'sed "s/";/" CASCADE;/"'

- 731
- 11
- 11
A solution to remove database and migrations manually.
at the same level of manage.py
, create clean.py
import os
def recursor(dirpath):
# print(dirpath)
delfiles = []
deldirs = []
with os.scandir(dirpath) as l1:
for e1 in l1:
if not e1.is_file():
with os.scandir(e1.path) as l2:
for e2 in l2:
if e2.name == 'migrations':
with os.scandir(e2.path) as l3:
for e3 in l3:
if not e3.name == '__init__.py':
print(e3.path)
if e3.is_file():
delfiles.append(e3.path)
else:
deldirs.append(e3.path)
with os.scandir(e3.path) as l4:
for e4 in l4:
delfiles.append(e4)
yn = input('are you sure to delete all the files above?(y/n)')
if yn == 'y':
for dp in delfiles:
os.remove(dp)
for dp in deldirs:
os.rmdir(dp)
recursor(os.path.dirname(os.path.realpath(__file__)))
delete db.sqlite3
file and run clean.py

- 2,621
- 19
- 35