开始你的第一个Django应用【Python web实战】

在这篇教程中,咱们将设置你的数据库,建立你的第一个模型,并快速介绍Django的自动生成的管理站点。

ps注意不少人学Python过程当中会遇到各类烦恼问题,没有人帮答疑容易放弃。为此小编建了个Python全栈免费答疑.裙 :七衣衣九起起巴而五(数字的谐音)转换下能够找到了,不懂的问题有老司机解决里面还有最新Python教程项目可拿,,一块儿相互监督共同进步!python

数据库配置

如今打开mysite/settings.py这是一个普通的python模块,模块变量表示Django的设定。mysql

默认状况下,Django配置使用SQLite数据库。若是你是数据库初学者,或者只是感兴趣想随便试试Django,这是最简单的选择。SQLite包含在Python内,所以你不须要安装任何其余东西来支持你的数据库。因此当你开始你的第一个真实项目时,你会想要使用一个更具扩展性的数据库,好比PostgreSQL,以免数据库切换引起的麻烦。sql

若是你但愿使用其余数据库,安装合适的数据库绑定而且在DATABASES'default'项目中修改keys以匹配数据库链接设置:shell

  • ENGINE
    好比 'django.db.backends.sqlite3', 'django.db.backends.postgresql', 'django.db.backends.mysql', or 'django.db.backends.oracle'。还有不少其余后端也有提供。详情请见数据库

  • NAME
    你数据库的名字。若是你使用SQLite,数据库将是你计算机上的一个文件,这种状况下,NAME应该是这个文件的完整绝对路径,包括文件名。默认值os.path.join(BASE_DIR, 'db.sqlite3')将文件春处在项目目录中。django

若是你不使用SQLite做为你的数据库,请务必添加USER, PASSWORD, 以及HOST。更多详情后端

写给其余用户的使用者
若是你在使用SQLite以外的数据库,请确保你使用前已经建立了数据库,请在你的数据库里使用CREATE DATABASE database_name;浏览器

同时确保mysite/settings.py拥有建立数据库的权限。这样就能够自动建立一个在后面的教程中须要的测试数据库。服务器

若是你正在使用SQLite,你不须要提早建立任何东西,数据库文件会在必要的时候自动建立。网络

当你开始编辑你的mysite/settings.py,设置你的TIME_ZONE为你的时区。

另外,注意INSTALLED_APPS放在文件最上面,它承载着这个Django实例中全部活动的Django应用的名字,应用能够被使用于多个项目中,你能够打包分发他们让别人在别的项目中使用。

默认状况下,INSTALLED_APPS随Django包含着几个应用。

  • django.contrib.admin管理站点,你能当即使用上。
    -django.contrib.auth认证系统。
    -django.contrib.contenttypes内容类型的框架
    -django.contrib.sessions session框架
    -django.contrib.messages messaging框架
    -django.contrib.staticfiles 静态文件管理

这些应用默认包括在内以方便开发者使用。

其中一些应用程序,须要至少一个数据库表才能使用,所以咱们须要在数据库中建立表,而后才能使用。请使用如下的命令:

python manage.py migrate

migrate命令查看INSTALLED_APPS的设置,并根据mysite/settings.py文件中的数据库设置建立须要的数据库表。若是你感兴趣的话,打开数据库命令行,输入如下命令来看看Django帮你建立了什么。

  • \dt(PostgreSQL),
  • SHOW TABLES;(MySQL),
  • .schema(SQLite),
  • SELECT TABLE_NAME FROM USER_TABLES;(Oracle)

写给极简主义者
正如咱们上面所说,咱们包含了默认应用为了涵盖常规使用,但并非每一个人都须要它们。若是你不须要,请在运行migrate以前,从INSTALLED_APPS中随意把注释掉或者删掉对应的代码。migrate命令只会运行INSTALLED_APPS中的应用。


建立模型

如今,咱们使用额外的元数据来定义你的模型(本质上就是你的数据库布局)。

模型的哲学
一个模型是关于您的数据的惟一的肯定的来源。它包含着您正在存储的数据的基本字段和行为。Django听从DRY原则。咱们的目标是在一个地方定义您的数据模型而后自动地从中获取数据。这就包括了迁移在里面。举个例子,不像Ruby on Rails,Django的迁移彻底源自您的数据模型,而且本质上只是Django能够经过更新数据库模式来匹配当前模型的历史。

在咱们这个简单的投票应用中,咱们会建立两个模型:问题(question)和选择(choice)。一个问题有一个问题内容和一个发布时间。一个选择有选择的文本和投票计数器。每一个选择都会和一个问题关联。

这些概念经过简单的python类就能够表现出来。按照如下代码,编辑你的polls/models.py文件。

polls/models.py
from django.db import models

class Question(models.Model): question_text = models.CharField(max_length=200) pub_date = models.DateTimeField('date published')

class Choice(models.Model): question = models.ForeignKey(Question, on_delete=models.CASCADE) choice_text = models.CharField(max_length=200) votes = models.IntegerField(default=0)

这些代码很是明确。每一个模型经过一个继承自django.db.models.Model的类来表示。每一个模型都有一些类变量,每一个变量都表示模型中的数据库字段。

每一个字段经过实例中的一个字段类表示,好比CharField是字符字段,DateTimeField是时间字段。这会告诉Django每一个字段保存着什么类型的数据。

每一个字段实例的名字(好比question_textpub_date)是字段的对机器友好的格式的名字,你之后能够在你的Python代码中使用这个值,你的数据库也会用它做为列名称。

你可使用(可选的)第一个位置参数做为指定的可读的名称。他能够用于Django的几个introspective(内省)部分,同时做为文档。若是没有提供,则Django将使用机器可读的名称做为名字。在这个例子中,咱们只对Question.pub_date定义了一个名字。对于其余全部的字段都会默认使用本身的机器名做为名字。

有些字段类有一些必须的参数要填。举例,CharField要求你给出最大长度max_length。这不只会用在数据库中,也会在验证中使用,后面咱们会讲到。

一个字段也能够拥有不少可选的参数,好比咱们能够看到,咱们班votes的默认值设成了0。

最后一点,注意关系是由外键定义的。这告诉Django,每个Choice都和只和一个问题相关。Django支持全部常见的数据库关系:多对一,多对多,一对一。


激活模型(activating models)

这个简单的模型告诉了Django不少信息。经过它,Django能够作到:

  • 为这个APP建立一个数据库对象集合
  • 建立一个Python数据库访问API来访问问题和选项的对象。

可是首先,咱们应该告诉咱们的项目,polls应用已经被安装了。

Django哲学小课堂
Django的应用是可插拔的。您能够在多个项目中使用某个应用程序,你能够分发应用程序,由于他们并非和给定的Django安装绑定的。

为了把对应的应用包括进咱们的项目中,咱们须要在INSTALLED_APPS设置中添加对其配置类的引用。PollsConfig类在polls/app.py文件中,路径是polls.apps.PollsConfig。编辑mysite/settings.py文件,添加路径到INSTALLED_APPS设置中。

mysite/settings.py
INSTALLED_APPS = [ 'polls.apps.PollsConfig', 'django.contrib.admin', 'django.contrib.auth', 'django.contrib.contenttypes', 'django.contrib.sessions', 'django.contrib.messages', 'django.contrib.staticfiles', ]

如今Django已经知道要把polls应用囊括在内了,下面运行另外一条命令:

python manage.py makemigrations polls

你会看到相似下面的结果:

Migrations for 'polls': polls/migrations/0001_initial.py: -Creat model Choice -Create model Question -Add field question to choice

经过运行makemigrations,你能够告诉Django你已经对你的model作出了一些改变,而且你但愿这些改变能够做为migration存储起来。(在如今的例子里是建立了一个新的model)

Django经过Migration来存储你的模型(也便是数据库对象)的变化。他们只是硬盘上的一些文件。若是你想,你能够为你的新模型读取一个Migration(迁移);也就是polls/migrations/0001_initial.py文件。不用担忧,你并不须要每次Django做出改变都要读取它们,可是若是你想手动调整Django如何改变内容,那么它们是被设计为能够人为编辑的。

有一个命令能够帮你运行migration而且自动管理你的数据库对象,也就是咱们稍后会介绍的migrate(迁移)。可是首先让咱们看看migration会运行什么样的SQL。sqlmigrate命令接受迁移名称,而且返回其SQL:

python manage.py sqlmigrate polls 0001

你应该会看到相似下面的结果

BEGIN;
--
-- *Create model Choice*
--
CREATE TABLE "polls_choice" ( "id" serial NOT NULL PRIMARY KEY, "choice_text" varchar(200) NOT NULL, "votes" integer NOT NULL );
--
-- *Create model Question*
--
CREATE TABLE "polls_question" ( "id" serial NOT NULL PRIMARY KEY, "question_text" varchar(200) NOT NULL, "pub_date" timestamp with time zone NOT NULL );
--
--*Add field question to choice*
--
ALTER TABLE "polls_choice" ADD COLUMN "question_id" integer NOT NULL;
ALTER TABLE "polls_choice" ALTER COLUMN "question_id" DROP DEFAULT;
CREATE INDEX "polls_choice_7aa0f6ee" ON "polls_choice" ("question_id");
ALTER TABLE "polls_choice" ADD CONSTRAINT "polls_choice_question_id_246c99a640fbbd72_fk_polls_question_id" FOREIGN KEY ("question_id") REFERENCES "polls_question" ("id") DEFERRABLE INITIALLY DEFERRED;
COMMIT;

注意:

  • 具体的输出会根据你如何使用的数据库而变化,上面的例子是根据PostgreSQL写的。
  • 表的名字会根据应用的名字以及模型的小写名自动生成(你能够覆盖这个行为)
  • 主键会自动生成(你能够覆盖这个)
  • 按照惯例,django将"_id"附加到外键字段名称。
  • 它根据你使用的数据库量身打造,所以数据库特定的字段类型好比auto_increment(MySQL), serial(PostgreSQL)或是integer primary key autoincrement (SQLite) 都会自动帮你处理。字段名的引用也一样如此。
  • sqlmigrate命令并不会真的让你的数据库迁移,只是打印到屏幕上,让你能够看到Django须要什么SQL。这对于检查Django在干什么或者有须要SQL脚本更改的数据库管理员很是有用。

若是你感兴趣,你还能够运行python manage.py check,这会不进行任何迁移,不接触数据库来检查你的项目有没有什么问题。

如今,再次运行migrate建立你的模型吧。

`$ python manage.py migrate
Operations to perform:
Apply all migrations: admin, auth, contenttypes, polls, sessions

Running migrations:
Rendering model states... DONE
Applying polls.0001_initial... OK`

migrate 命令接收全部未应用的迁移(Django经过一个叫作django_migrations的特殊表聊跟踪哪些迁移被应用了)并根据数据库运行他们。本质上是将你对模型的更改与数据库对象进行同步。

迁移很是强大,他可让你一边建设你的项目,一边慢慢地改变你的数据库,并且不用删除你的数据库或者表,或者建立一个新的。它专门用于实时升级数据库,而不会丢失数据。咱们将在本教程的后续部分中更深刻地介绍它们,可是如今,请记住进行模型更改的三步指南:

  • 更改你的模型(在 models.py 中)。
  • 运行 python manage.py makemigrations 来建立这些更改的迁移
  • 运行 python manage.py migrate 将这些更改应用于数据库。

Django有单独的命令来制做和应用迁移的缘由是由于您能够提交迁移到版本控制系统并将其发送到您的应用程序; 它们不只可使您的开发更容易,并且还能够被其余开发人员和生产中使用。

请阅读 django-admin文档,了解有关 manage.py 能够执行的操做的完整信息。


玩转API

如今,咱们一块儿进入交互式的Python shell,并使用Django提供的免费API。要调用Python shell,请使用一下命令:

python manage.py shell

咱们没有简单的输入python而是使用这个命令,由于manage.py设置了DJANGO_SETTINGS_MODULE环境变量,这给了Django提供了你的mysite/settings.py文件的Python导入路径。

绕过manage.py
若是你不想用manage.py也没问题, 只要将DJANGO_SETTINGS_MODULE
环境变量设置给mysite.settings,打开一个普通的python shell,而后设置Django:
>>>import django
>>>django.setup()

若是这引起了一个AttributeError,你也许用的Django版本不是1.11,请更换不一样版本的教程或者升级你的Django。

你必须在manage.py所在的目录下运行Python,或者保证目录在Python路径上,import mysite才能正常工做。

更多相关信息,请参考django-admin documentation

进入了shell后,咱们来看看database API:

>>> from polls.models import Question, Choice # Import the model classes we just wrote.

# No questions are in the system yet.
>>> Question.objects.all()
<QuerySet []>

# Create a new Question.
# Support for time zones is enabled in the default settings file, so
# Django expects a datetime with tzinfo for pub_date. Use timezone.now()
# instead of datetime.datetime.now() and it will do the right thing.
>>> from django.utils import timezone
>>> q = Question(question_text="What's new?", pub_date=timezone.now())

# Save the object into the database. You have to call save() explicitly.
>>> q.save()

# Now it has an ID. Note that this might say "1L" instead of "1", depending
# on which database you're using. That's no biggie; it just means your
# database backend prefers to return integers as Python long integer
# objects.
>>> q.id
1

# Access model field values via Python attributes.
>>> q.question_text
"What's new?"
>>> q.pub_date
datetime.datetime(2012, 2, 26, 13, 0, 0, 775217, tzinfo=<UTC>)

# Change values by changing the attributes, then calling save().
>>> q.question_text = "What's up?"
>>> q.save()

# objects.all() displays all the questions in the database.
>>> Question.objects.all()
<QuerySet [<Question: Question object>]>

等一下!<>彻底是一个没有任何帮助的表达,让咱们编辑问题模型(在polls/models.py文件中)来解决这个问题。而后添加__str__()方法到Question和Choice。

polls/models.py
from django.db import models
from django.utils.encoding import python_2_unicode_compatible

@python_2_unicode_compatible # only if you need to support Python 2
class Question(models.Model): def __str__(self): return self.question_text

@python_2_unicode_compatible # only if you need to support Python 2
class Choice(models.Model): def __str__(self): return self.choice_text

__str__()方法的添加是很重要的,不光是为了你本身处理交互提示的方便,也是由于对象的展现是经过Django的自动生成admin的。

注意这些都是普通Python方法,如今咱们添加一个自定义方法,为了演示使用。

polls/models.py
import datetime

from django.db import models
from django.utils import timezone

class Question(models.Model): def was_published_recently(self): return self.pub_date >= timezone.now() - datetime.timedelta(days=1)

请注意,添加import datetime和django.utils import timezone能够分别在django.utils.timezone中引用Python的标准datetime模块和Django的时区相关实用程序。若是您不熟悉Python中的时区处理,您能够在时区文档.中了解更多信息。

保存这些更改并经过再次运行python manage.py shell启动一个新的Python shell:

>>> from polls.models import Question, Choice

# Make sure our __str__() addition worked.
>>> Question.objects.all()
<QuerySet [<Question: What's up?>]>

# Django provides a rich database lookup API that's entirely driven by
# keyword arguments.
>>> Question.objects.filter(id=1)
<QuerySet [<Question: What's up?>]>
>>> Question.objects.filter(question_text__startswith='What')
<QuerySet [<Question: What's up?>]>

# Get the question that was published this year.
>>> from django.utils import timezone
>>> current_year = timezone.now().year
>>> Question.objects.get(pub_date__year=current_year)
<Question: What's up?>

# Request an ID that doesn't exist, this will raise an exception.
>>> Question.objects.get(id=2)
Traceback (most recent call last):
...
DoesNotExist: Question matching query does not exist.

# Lookup by a primary key is the most common case, so Django provides a
# shortcut for primary-key exact lookups.
# The following is identical to Question.objects.get(id=1).
>>> Question.objects.get(pk=1)
<Question: What's up?>

# Make sure our custom method worked.
>>> q = Question.objects.get(pk=1)
>>> q.was_published_recently()
True

# Give the Question a couple of Choices. The create call constructs a new
# Choice object, does the INSERT statement, adds the choice to the set
# of available choices and returns the new Choice object. Django creates
# a set to hold the "other side" of a ForeignKey relation
# (e.g. a question's choice) which can be accessed via the API.
>>> q = Question.objects.get(pk=1)

# Display any choices from the related object set -- none so far.
>>> q.choice_set.all()
<QuerySet []>

# Create three choices.
>>> q.choice_set.create(choice_text='Not much', votes=0)
<Choice: Not much>
>>> q.choice_set.create(choice_text='The sky', votes=0)
<Choice: The sky>
>>> c = q.choice_set.create(choice_text='Just hacking again', votes=0)

# Choice objects have API access to their related Question objects.
>>> c.question
<Question: What's up?>

# And vice versa: Question objects get access to Choice objects.
>>> q.choice_set.all()
<QuerySet [<Choice: Not much>, <Choice: The sky>, <Choice: Just hacking again>]>
>>> q.choice_set.count()
3

# The API automatically follows relationships as far as you need.
# Use double underscores to separate relationships.
# This works as many levels deep as you want; there's no limit.
# Find all Choices for any question whose pub_date is in this year
# (reusing the 'current_year' variable we created above).
>>> Choice.objects.filter(question__pub_date__year=current_year)
<QuerySet [<Choice: Not much>, <Choice: The sky>, <Choice: Just hacking again>]>

# Let's delete one of the choices. Use delete() for that.
>>> c = q.choice_set.filter(choice_text__startswith='Just hacking')
>>> c.delete()

有关模型关系的更多信息,请参阅访问 相关文档. 有关如何使用双下划线经过API执行字段查找的更多信息,请参阅 Field lookups. 有关数据库API的完整详细信息,请参阅咱们的 Database API reference.


Django Admin介绍

"Django的哲学"小课堂
Django管理站点是为你的员工或者客户的简单的添加,更改,删除这些繁琐工做而设计的。Django管理站点会彻底自动生成模型的管理站。

Django当年建立于新闻编辑室,为内容管理而生的,“内容发布者”和“公共”网站之间的界限很是明确。网站管理人员使用该系统添加新闻故事,事件,体育比分等,该内容显示在公共站点上。 Django解决了为站点管理员建立统一界面来编辑内容的问题。

这个管理站点不打算由网站访问者使用。这是网站经理。

建立一个管理员用户

首先,咱们须要建立一个用户来登陆管理站点。使用下面的命令:
python manage.py createsuperuser
输入你想要的用户名
Username: admin
输入邮箱地址
Email address: admin@example.com
最后输入你的密码两次。
Password: **********
Password (again): *********
Superuser created successfully.

开启你的开发服务器

django管理站点会自动启动,咱们只要启动开发服务器就能够来一块儿探索它了。
使用python manage.py runserver开启服务器。
如今打开一个浏览器,而且去/admin/-例如http://127.0.0.1:8000/admin/你应该会看到Django administration的登陆界面。

进入admin管理站点。
总结:不少人学Python过程当中会遇到各类烦恼问题,没有人帮答疑容易放弃。为此小编建了个Python全栈免费答疑.裙 :七衣衣九起起巴而五(数字的谐音)转换下能够找到了,不懂的问题有老司机解决里面还有最新Python教程项目可拿,,一块儿相互监督共同进步!

本文的文字及图片来源于网络加上本身的想法,仅供学习、交流使用,不具备任何商业用途,版权归原做者全部,若有问题请及时联系咱们以做处理。

相关文章
相关标签/搜索