默認(rèn)情況下,配置使用SQLite。如果你是數(shù)據(jù)庫新手,或者想嘗試學(xué)習(xí)Django,這是最簡單的選擇。SQLite包含在Python,所以不需要安裝任何東西來支持你的數(shù)據(jù)庫。當(dāng)開始你的第一個(gè)真正的項(xiàng)目,可能需要使用更強(qiáng)大的數(shù)據(jù)庫如:PostgreSQL,MySQL等,可以配置數(shù)據(jù)庫切換就可以了。
如果你不使用SQLite作為數(shù)據(jù)庫,而使用其他設(shè)置,如USER, PASSWORD, 和 HOST 必須加入。欲了解更多詳細(xì)信息,請參閱用于數(shù)據(jù)庫的參考文檔。
此外,請注意,在該文件的頂部的 INSTALLED_APPS 設(shè)置。它包含了很多在本Django示例中激活的所有 Django 的應(yīng)用程序的名稱。 應(yīng)用程序可以在多個(gè)項(xiàng)目中使用,你可以打包給別人并在他們的項(xiàng)目分發(fā)使用。
其中的一些應(yīng)用程序使用至少一個(gè)數(shù)據(jù)庫表,所以我們需要在數(shù)據(jù)庫中創(chuàng)建的表才可以使用它們。要做到這一點(diǎn),運(yùn)行以下命令:
C:\Python27\mysite>python manage.py migrate Operations to perform: Apply all migrations: admin, contenttypes, auth, sessions Running migrations: Rendering model states... DONE Applying contenttypes.0001_initial... OK Applying auth.0001_initial... OK Applying admin.0001_initial... OK Applying admin.0002_logentry_remove_auto_add... OK Applying contenttypes.0002_remove_content_type_name... OK Applying auth.0002_alter_permission_name_max_length... OK Applying auth.0003_alter_user_email_max_length... OK Applying auth.0004_alter_user_username_opts... OK Applying auth.0005_alter_user_last_login_null... OK Applying auth.0006_require_contenttypes_0002... OK Applying auth.0007_alter_validators_add_error_messages... OK Applying sessions.0001_initial... OK C:\Python27\mysite>
migrate 命令著眼于INSTALLED_APPS設(shè)置并創(chuàng)建根據(jù)您的 mysite/settings.py 文件數(shù)據(jù)庫設(shè)置,并隨應(yīng)用程序數(shù)據(jù)庫遷移任何數(shù)據(jù)庫表(我們將在以后的教程討論)。你會看到每個(gè)適用移植的消息。 如果有興趣,運(yùn)行命令行在你的數(shù)據(jù)庫客戶端,列如類型\dt (PostgreSQL), SHOW TABLES; (MySQL), .schema (SQLite), 或 SELECT TABLE_NAME FROMUSER_TABLES; (Oracle) 以顯示Django所創(chuàng)建的表。
在我們的簡單調(diào)查的應(yīng)用程序,我們將創(chuàng)建兩個(gè)模型:Question 和 Choice。Question有一個(gè)問題標(biāo)題和發(fā)布日期。Choice有兩個(gè)字段:選擇文本和票數(shù)。每個(gè)選項(xiàng)都與一個(gè)問題關(guān)聯(lián)。
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)
該代碼是直接的。每個(gè)模型是django.db.models.Model類的子類。 每個(gè)模型具有許多類變量,每一個(gè)在模型變量與數(shù)據(jù)庫表的字段關(guān)聯(lián)。
每個(gè)字段由 Field 類實(shí)例表示 – 例如,CharField表示字符型字段,DateTimeField表示日期時(shí)間字段。這告訴Django 每個(gè)字段保存的數(shù)據(jù)類型。
每個(gè)Field實(shí)例(例如,question_text或pub_date)的名稱是字段的名稱,這是機(jī)器友好的格式。在Python代碼中使用這個(gè)值,數(shù)據(jù)庫將使用它作為列名。
最后,需要注意的是關(guān)系的定義,這里使用了外鍵。這告訴 Django 每個(gè)選項(xiàng)關(guān)聯(lián)一個(gè)問題。 Django支持所有常見的數(shù)據(jù)庫關(guān)系:多對一,多對多以及一對之一。
INSTALLED_APPS = [
'polls.apps.PollsConfig',
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
]
C:\Python27\mysite>python manage.py makemigrations polls
Migrations for 'polls':
0001_initial.py:
- Create model Choice
- Create model Question
- Add field question to choice
C:\Python27\mysite>
遷移是Django怎么存儲您更改的模型(由你的數(shù)據(jù)庫架構(gòu)決定)- 它們只是在磁盤上的文件。您如果喜歡可以讀取移植新的模型,它在文件 polls/migrations/0001_initial.py。你不會希望Django每一次都讀取它們,不過將它們設(shè)計(jì)成人可編輯的,你要知道Django是如何變化的并手動(dòng)調(diào)整。
還有將運(yùn)行migrations,自動(dòng)管理數(shù)據(jù)庫模式(表)命令 - 這就是所謂的遷移,讓我們看看SQL了解移植運(yùn)行。 sqlmigrate 命令將移植名稱返回SQL顯示:
$ python manage.py sqlmigrate polls 0001
C:\Python27\mysite>python manage.py sqlmigrate polls 0001
BEGIN;
--
-- Create model Choice
--
CREATE TABLE "polls_choice" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "c
hoice_text" varchar(200) NOT NULL, "votes" integer NOT NULL);
--
-- Create model Question
--
CREATE TABLE "polls_question" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT,
"question_text" varchar(200) NOT NULL, "pub_date" datetime NOT NULL);
--
-- Add field question to choice
--
ALTER TABLE "polls_choice" RENAME TO "polls_choice__old";
CREATE TABLE "polls_choice" ("id" integer NOT NULL PRIMARY KEY AUTOINCREMENT, "c
hoice_text" varchar(200) NOT NULL, "votes" integer NOT NULL, "question_id" integ
er NOT NULL REFERENCES "polls_question" ("id"));
INSERT INTO "polls_choice" ("choice_text", "votes", "id", "question_id") SELECT
"choice_text", "votes", "id", NULL FROM "polls_choice__old";
DROP TABLE "polls_choice__old";
CREATE INDEX "polls_choice_7aa0f6ee" ON "polls_choice" ("question_id");
COMMIT;
C:\Python27\mysite>
遷移命令將所有還沒有被應(yīng)用的遷移(Django跟蹤哪些是使用數(shù)據(jù)庫中的一個(gè)特殊的表名為django_migrations應(yīng)用)運(yùn)行它們在數(shù)據(jù)庫中 - 基本上是,將使用模型在數(shù)據(jù)庫模式的變化同步。
C:\Python27\mysite>python manage.py shell Python 2.7.10 (default, May 23 2015, 09:44:00) [MSC v.1500 64 bit (AMD64)] on wi n32 Type "help", "copyright", "credits" or "license" for more information. (InteractiveConsole) >>>
只需鍵入“python” 來代替,因?yàn)閙anage.py設(shè)置DJANGO_SETTINGS_MODULE環(huán)境變量,這給Django Python 導(dǎo)入路徑到 mysite/settings.py文件。
>>> import django >>> django.setup()
>>> from polls.models import Question, Choice # Import the model classes we just wrote. # No questions are in the system yet. >>> Question.objects.all() [] # 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() [<Question: Question object>]這里需要等待一會兒. <Question: Question object>完全是這個(gè)對象的無用表示。讓我們來解決這個(gè)問題:通過編輯Question模型(在polls/models.py 文件),并添加一個(gè)__str__() 方法到這兩個(gè)Question 和 Choice 模型:polls/models.py文件內(nèi)容如下:
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
注意,這些都是正常的Python方法。讓我們添加一個(gè)自定義的方法,這里只是為了演示: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 和from django.utils import timezon,引用Python的標(biāo)準(zhǔn)的datetime模塊和Django的時(shí)區(qū)相關(guān)的實(shí)用程序在django.utils.timezone,如果不熟悉在Python的時(shí)區(qū)處理,可以閱讀時(shí)區(qū)支持文檔。
>>> from polls.models import Question, Choice
# Make sure our __str__() addition worked.
>>> Question.objects.all()
[<Question: What's up?>]
# Django provides a rich database lookup API that's entirely driven by
# keyword arguments.
>>> Question.objects.filter(id=1)
[<Question: What's up?>]
>>> Question.objects.filter(question_text__startswith='What')
[<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()
[]
# 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()
[<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)
[<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()
c:\python27\mysite> python manage.py createsuperuser
Username: admin
Email address: admin@yiibai.com
Password: ********** Password (again): ********* Superuser created successfully.
c:\python27\mysite>python manage.py runserver
現(xiàn)在,打開Web瀏覽器,進(jìn)入“/admin/” 本地域名- 例如, http://127.0.0.1:8000/admin/ 應(yīng)該看到管理員登錄界面:
由于移在默認(rèn)情況下開啟,登錄屏幕可能會顯示在你自己的語言, 由于翻譯在默認(rèn)情況下開啟,登錄屏幕可能會顯示在你自己的語言,

只有一件事要做:我們需要告訴管理員這個(gè)Question對象有一個(gè)管理界面。要做到這一點(diǎn),打開 polls/admin.py文件,并修改它如下:
from django.contrib import admin from .models import Question admin.site.register(Question)

點(diǎn)擊“Questions”。現(xiàn)在,在“change list”頁面查看問題。該頁面顯示數(shù)據(jù)庫中的所有問題,并允許您選擇其中一個(gè)進(jìn)行更改。還有我們先前創(chuàng)建的問題:

修改“Date published”點(diǎn)擊“Today”和“Now”快捷方式。然后點(diǎn)擊“Save and continue editing.”,然后點(diǎn)擊“History”在右上角。你會看到一個(gè)頁面,列出通過Django管理到這個(gè)對象的所有變化,修改人用戶名和時(shí)間戳:

代碼下載:http://pan.baidu.com/s/1jGR3wDg