重置Django PostgreSQL数据库的简单方法?

32

我能够按照以下步骤重置Django PostgreSQL数据库:

  1. 删除迁移文件
  2. 进入psql命令提示符。连接到数据库。drop schema public cascade; create schema public;
  3. 不幸的是,第二步似乎已经删除了我的用户角色和权限,因此我回到psql命令提示符并重新创建它们。
  4. 第二步还意味着我需要在psql命令提示符中运行以下命令:grant usage on schema public to public; grant create on schema public to public;
  5. 第二步还删除了我创建的标准Django用户,因此我需要重新创建这些用户。
  6. python manage.py makemigrations && python manage.py migrate

我目前正在对我的模型进行更改并测试每个更改。我没有任何需要保留的数据。当迁移不起作用时,是否有比上述方法更简单的方法来重置数据库?

我至少想用其他方法替换第二步,以便跳过步骤3-5。

7个回答

48

最简单的方法可能是重新创建整个数据库。在Ubuntu中,操作如下:

sudo su postgres
psql
drop database your_database_name;
create database your_database_name with owner user_you_use_in_django;
\q
exit

就这样,你已经清理了数据库。为了让它准备好工作,你需要运行迁移命令 python manage.py migrate

如果你是一个人在项目中工作,你可以删除并重新创建迁移文件。


1
谢谢!但这并没有简化我的操作步骤。我仍然需要重新创建默认的Django用户,并且仍然需要将用户角色更改为我想要的角色。 - user1283776
1
如果您需要在重新创建数据库后保留某些数据,则可以使用固定数据或一些自动化脚本。 - Ihor Pomaranskyy

10

使用Python

from django.db import connection

with connection.cursor() as cursor:
    cursor.execute("DROP SCHEMA public CASCADE;")
    cursor.execute("CREATE SCHEMA public;")

then,

python manage.py migrate

9

我成功地“重置了我的django postgreSQL数据库”(同时不丢失数据)。

更新我的models.py后,使用./manage.py makemigrations./manage.py migrate是不可能的,因为需要重命名的表彼此循环指向。Django无法自动完成这个任务。

所以,我选择备份我的数据。清空。删除表格。更新我的models.py文件。修改我创建的(json)备份(使用./manage.py datadump > fileName.json),以反映我的更新列名称/表名称。然后,我使用./manage.py migrate./manage.py makemigrations重新创建了数据库。然后,我使用./manage.py loaddata fileName.json将我的备份加载回数据库的新创建表中。

我采取的确切步骤:

  1. 首先,我备份了我的服务器/VM。
  2. ./manage.py dumpdata > db.json
  3. ./manage.py flush
  4. 选择“Yes”[注意这将删除所有数据!]
  5. 从--myDataBaseName--删除所有表格
  6. 删除您的迁移文件夹
  7. 对models.py文件进行更改(如果有任何更改)
  8. ./manage.py migrate
  9. ./manage.py makemigrations --myAppName--
  10. ./manage.py migrate --myAppName--
  11. 进入db.json并删除contenttype相关的内容。在某些情况下,您可能还需要删除(并在步骤12之后手动种子)auth_permissions相关条目。将修改后的db.json另存为db_new.json,以防万一事情变得很糟糕,您需要将所有内容恢复到原来的状态!
  12. ./manage.py loaddata db_new.json

8
如果您使用的是 Docker/Composer,请运行 docker-compose down,然后再运行 migrate 命令进行迁移。

8
对我来说,这是正确的起点!我需要稍微改一下: docker-compose down -v,其中 -v 的意思是同时删除卷; docker-compose up --detach db 是将(现在为空的)数据库重新启动的命令; 然后相同的 python manage.py migrate - Ezra
-v 是我的问题的答案。谢谢! - Aaron

2
如果您想要完全重新开始,您需要删除数据库。这意味着您需要执行以下步骤:重新创建它,添加权限,重新生成所有迁移并重新运行它们。
好消息是,您可以很容易地将所有这些步骤合成一条或几条命令。
新的迁移文件
如果您删除整个文件夹,您需要运行“makemigrations”命令,并提及所有应用程序名称。如果您经常这样做,那么这会很麻烦。为了让Django看到需要迁移的应用程序,您应该保留migrations文件夹以及其中的__init__.py文件。
以下是一个 bash 命令:
find . -path "*migrations*" -not -regex ".*__init__.py" -a -not -regex ".*migrations" | xargs rm -rf

然后按照通常的方式操作(这将为之前有迁移的所有应用程序创建迁移):

python manage.py makemigrations

重置PostgreSQL数据库
在控制台中运行以下命令:
psql -c "drop database <db_name>;"
psql -c "create database <db_name>;"
psql -c "grant all on database <db_name> to <db_user>;"

最后,使用以下命令重新运行迁移:

python manage.py migrate

超级用户

显然,您将缺少一个超级用户,因此您可能还需要执行以下操作:

python manage.py createsuperuser

没有输入的方法是将Python代码传送到shell中执行:

echo "from django.contrib.auth import get_user_model; User = get_user_model(); User.objects.create_superuser('admin', 'badmin@myproject.com', 'pa$$w0rd')" | python manage.py shell

一般来说,关于这些非常常见的操作 - 自己动手写点bash吧。在多年与不仅限于Django的工作中,它为我节省了许多累积的时间。因为比单行命令更好的是,拥有一个存储更多这些方便函数的整个实用文件。然后你就可以只运行类似这样的东西:

django --reset_migrations
db --reset <my_db>
django --migrate

如果你发现自己一直在重复同样的几个操作,甚至可以将它们聚合成一行。

reset_django() {
    find . -path "*migrations*" -not -regex ".*__init__.py" -a -not -regex ".*migrations" | xargs rm -rf
    python manage.py makemigrations
    psql -c "drop database <db_name>;"
    psql -c "create database <db_name>;"
    psql -c "grant all on database <db_name> to <db_user>;"
    python manage.py migrate
    echo "from django.contrib.auth import get_user_model; User = get_user_model(); User.objects.create_superuser('admin', 'badmin@myproject.com', 'pa$$w0rd')" | python manage.py shell
}

我的灵感工具

#!/bin/bash


django() {

    project_name=$(basename $PWD)
    project_path="$PWD"
    manage_path="${project_path}/${project_name}/manage.py"

    if [ ! -f $manage_path ] ; then  # No project/manage.py
        echo "Error: Could not locate Django manage.py file."
        return -1
    fi

    if [ $# -eq 0 ] ; then
        echo "Django project detected."
    fi

    while [ ! $# -eq 0 ]
        do
            case "$1" in

                --help | -h)
                        echo "Django shortcut, unknown commands are forwarded to manage.py"
                        echo "  -c, --check         Run Django manage.py check."
                        echo "  --req           Install requirements."
                        echo "  -r, --run           Run server."
                        echo "  -s, --shell         Run Django shell plus."
                        echo "  -sd, --shell            Run Django shell plus. Debug DB (print sql)"
                        echo ""
                    ;;

                --check | -c)
                        python $manage_path check
                    ;;

                --shell | -s)
                        python $manage_path shell_plus --bpython
                    ;;

                --shell | -sd)
                        python $manage_path shell_plus --bpython --print-sql
                    ;;

                --run | -r)
                        python $manage_path runserver
                    ;;

                --req)
                        pip install -r $project_path/requirements.txt
                    ;;

                --mig | -m)
                        python $manage_path makemigrations
                        python $manage_path migrate
                    ;;

                --reset_migrations)
                        find . -path "*migrations*" -not -regex ".*__init__.py" -a -not -regex ".*migrations" | xargs rm -rf
                        python $manage_path makemigrations
                        ;;

                *)
                    python $manage_path "$@"
                    ;;

            esac
            shift
        done

}

1
我不明白为什么你认为需要删除迁移或数据库。 迁移的整个重点在于它们建立在之前的基础上; 你永远不应该需要删除并重新开始。 每次进行更改时只需执行makemigrations,一系列迁移应始终有效。稍后,您可能希望将一组迁移压缩成一个迁移,以提高速度,这也是本地支持的。但永远不要删除已经运行的迁移。

3
我想删除迁移文件,因为在运行manage.py migrate时出现了错误,我无法弄清楚如何修复它。 - user1283776
8
如果您的生产环境中尚未有数据库,那么删除迁移并重新创建不会有太大影响。 - cdvv7788
11
我认为这是错误的态度。开发人员不应该害怕任何代码。他们需要完全掌控整个过程,特别是在看法明确且有时很难掌握的框架方面。为了解决一个类似的问题,将类型转换(这是 Django 的内部问题),我回溯并重新编写了(迁移)历史记录。政府一直在这样做,为什么开发人员不能呢? - codervince
2
丹尼尔,有时候 ./manage.py makemigrations xyzAppName 无法正常工作。或者它生成的迁移文件在传递给 ./manage.py migrate xyzAppName 时没有正确运行。例如,循环依赖表(如果有人出于某种原因想要它们)不容易修改。 - Xandrix
我在这里支持Daniel。当你有一个生产数据库时,删除迁移可能会严重破坏事情...我曾经遇到过这种情况...它们被称为迁移,因为“迁移的整个重点是它们建立在之前发生的事情之上”。我完全同意这一点。 - Micromegas
显示剩余2条评论

-2

首先,您需要从项目中删除迁移文件。然后使用终端窗口运行psql数据库(确保与数据库和项目相关的任何东西都应关闭,以便不会运行db的任何实例)。 接下来,按照以下链接从终端窗口删除db https://www.postgresqltutorial.com/postgresql-drop-database/

希望这可以解决问题。我自己遇到了同样的问题,这些步骤解决了它。祝开发愉快!


这只是一个不同的、不太准确的问题描述。再次强调,这个未指明的需求认为移除迁移文件与删除或重新创建数据库有任何关系。 - user1600649
由于我对计算机科学非常新,所以这种方法似乎更适合我,并且在删除数据库后,我们可以从头开始重新创建它。如果您能分享适当的答案,我会很高兴。 - Ritesh Mukhopadhyay
你的回答使用了不同的词语,但与此答案基本相同。 - user1600649
1
请尽量不要使用链接,因为它们可能会消失,那么您的答案就无法帮助任何人。处理这种情况的好方法是引用文章的部分内容,然后仍然在此处留下链接。 - Sam Apostel
@SamApostel 当然,这个见解非常必要。 - Ritesh Mukhopadhyay

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接