Django数据模型动态增删字段(更改数据库模式)

来源:互联网 发布:知乐油烟机 编辑:程序博客网 时间:2024/06/01 16:19

当处理django模型修改的时候,使用syncdb命令无法达到目的,访问数据模型时会报这个错误。
Exception Value:

no such column: books_book.num_pages

原因是使用syncdb这个命令仅仅是创建数据库里还没有的表,它并不对你数据模型的修改进行同步,也不处理数据模型的删除如果你新增或修改数据模型里的字段,或是删除了一个数据模型,你需要手动在数据库里进行相应的修改。

查了官网的api,找到以下解决方法

添加字段

操作:

  1. 在你的模型里添加字段。

  2. 运行 manage.py sqlall [yourapp] 来测试模型新的 CREATE TABLE 语句。 注意为新字段的列定义。

  3. 开启你的数据库的交互命令界面(比如, psql mysql , 或者可以使用 manage.py dbshell )。 执行 ALTER TABLE 语句来添加新列。

  4. 使用Python的manage.py shell,通过导入模型和选中表单(例如, MyModel.objects.all()[:5] )来验证新的字段是否被正确的添加 ,如果一切顺利,所有的语句都不会报错。


删除字段

从Model中删除一个字段要比添加容易得多。 删除字段,仅仅只要以下几个步骤:

1. 删除字段,然后重新启动你的web服务器。

2. 用以下命令从数据库中删除字段:ALTER TABLE books_book DROP COLUMN num_pages;

如果你先从数据库中删除字段,Django将会立即抛出异常。


删除多对多关联字段

由于多对多关联字段不同于普通字段,所以删除操作是不同的。

从你的模型中删除ManyToManyField,然后重启web服务器。

用下面的命令从数据库删除关联表:DROP TABLE books_book_authors;

像上面一样,注意操作的顺序。


删除模型

删除整个模型要比删除一个字段容易。 删除一个模型只要以下几个步骤:

1. 从文件中删除你想要删除的模型,然后重启web 服务器models.py

2. 然后用以下命令从数据库中删除表:DROP TABLE books_book;

当你需要从数据库中删除任何有依赖的表时要注意(也就是任何与表books_book有外键的表 ),删除对应的字段。


附上models.py文件的代码(要尝试上面的步骤记得先同步数据模型python manage.py syncdb):

# Create your models here.class Publisher(models.Model):    name = models.CharField(max_length=30)    address = models.CharField(max_length=50)    city = models.CharField(max_length=60)    state_province = models.CharField(max_length=30)    country = models.CharField(max_length=50)    website = models.URLField()    def __unicode__(self):        return self.name    class Meta:        ordering = ['name']class Author(models.Model):    first_name = models.CharField(max_length=30)    last_name = models.CharField(max_length=40)    email = models.EmailField()    def __unicode__(self):        return u'%s %s' % (self.first_name, self.last_name)class Book(models.Model):    title = models.CharField(max_length=100)    authors = models.ManyToManyField(Author)    publisher = models.ForeignKey(Publisher)    publication_date = models.DateField()    num_pages = models.IntegerField(blank=True, null=True)    def __unicode__(self):        return self.title

0 0