Django入门实战手记:从0搭建一个Python网站的全过程
去年刚入行的时候,我接到公司的一个需求,要在两周内搭起一个内部使用的任务管理系统,用来追踪产品部门的需求、开发进度和上线状态。当时领导建议用Django,因为“快速成型”、“上手快”,但对我来说还是个陌生的名字。
说来也巧,虽然大学学过点Python,但Web开发完全是新手。不过好在有文档,有Stack Overflow,还有社区,硬是边学边干,两周内交出了一版可运行的基础系统。这段经历让我对Django有了非常扎实的第一印象,也想通过这篇文章,把我踩过的坑、学到的经验分享出来,帮助大家少走弯路,把注意力集中在真正重要的事情上。
项目背景:一个简单的任务管理系统

项目的初衷很简单——产品提出需求后,要有人去评估工作量、分配到人、设定截止时间、跟踪完成情况。我们需要一个界面化的工具,能展示任务列表、查看任务详情、修改状态,并且支持简单的搜索和排序。
技术选型考虑
我们团队技术栈以Python为主,之前做过一些数据分析的小系统,所以这次想试试看能不能用Python做前端加后端的全栈方案。经过讨论,我们选择了:
- Django 作为后端框架
- PostgreSQL 作为数据库(生产环境)
- Vue.js 搭配 Django 模板做简单前端(后来改成了前后端分离)
- 使用 SQLite 开发初期数据存储,后期迁移到 Postgres
- 使用 Gunicorn + Nginx 部署生产环境
初次接触:Django到底是怎么工作的?

刚开始装完Django,跑了个hello world,觉得还挺神奇:“就几行代码?真能启动服务?”然后按照官方教程一步步创建了第一个 app,设置了 model、view、url,感觉有点像搭积木的过程。
但说实话,真正开始开发之后才发现问题来了:
- URL路由咋配置才最合理?
- 页面渲染是用模板还是返回 JSON?
- 用户权限怎么控制?
- 数据库模型怎么设计比较科学?
- 如何部署到服务器?
这些问题,在初学者眼里都是迷雾重重。下面我会结合实际开发过程,讲讲我是怎么一步一步解决这些问题的。
第一步:创建项目和App

安装Django其实很简单,直接 pip 安装就行:
pip install django
然后新建项目:
django-admin startproject taskmanager
cd taskmanager
python manage.py runserver
访问 localhost:8000 就能看到 Django 的欢迎页面,说明项目跑起来了。
接下来是创建一个叫 tasks 的应用:
python manage.py startapp tasks
记得把这个 app 添加到 INSTALLED_APPS 里,否则会报错:
# settings.py
INSTALLED_APPS = [
...
'tasks',
]
第二步:设计数据库模型
这是我遇到的第一个难点。一开始我以为只要写几个类字段就能搞定,结果数据结构不清晰导致后面频繁修改 model,migration 出现各种冲突。
我们最终定义了一个简单的 Task 模型:
# tasks/models.py
from django.db import models
from django.contrib.auth.models import User
STATUS_CHOICES = (
('pending', '待处理'),
('in_progress', '进行中'),
('done', '已完成'),
)
class Task(models.Model):
title = models.CharField(max_length=255)
description = models.TextField(blank=True, null=True)
status = models.CharField(max_length=20, choices=STATUS_CHOICES, default='pending')
assignee = models.ForeignKey(User, on_delete=models.SET_NULL, null=True, blank=True)
created_at = models.DateTimeField(auto_now_add=True)
updated_at = models.DateTimeField(auto_now=True)
def __str__(self):
return self.title
模型完成后别忘了执行迁移命令:
python manage.py makemigrations
python manage.py migrate
第三步:编写视图与URL路由
视图部分我一开始就遇到了两个选择:要不要用 CBV(基于类的视图)?还是继续用 FBV(函数视图)?
我个人推荐新人先用函数视图,理解更直观。举个例子,下面是查看所有任务的视图:
# tasks/views.py
from django.shortcuts import render
from .models import Task
def task_list(request):
tasks = Task.objects.all()
return render(request, 'tasks/list.html', {'tasks': tasks})
然后设置路由:
# tasks/urls.py
from django.urls import path
from . import views
urlpatterns = [
path('', views.task_list, name='task_list'),
]
并在主项目的 urls.py 中 include 这个 app 的 url:
# taskmanager/urls.py
from django.urls import include, path
urlpatterns = [
path('tasks/', include('tasks.urls')),
]
这个时候,如果你访问 /tasks/ 应该就能看到一个空白页面了。
第四步:使用模板渲染页面
我最初是直接在 templates 目录下手动创建 HTML 文件。注意 Django 默认不会自动寻找 template,你要在 TEMPLATES 设置中加入你的模板目录路径:
# settings.py
TEMPLATES = [
{
...
'DIRS': [BASE_DIR / 'templates'],
...
}
]
比如我的页面结构是这样的:
templates/
└── tasks/
└── list.html
这个HTML文件里面可以使用模板变量,例如:
<!-- tasks/list.html -->
<h1>任务列表</h1>
<ul>
{% for task in tasks %}
<li>{{ task.title }} - {{ task.status }}</li>
{% endfor %}
</ul>
踩坑记录:那些年我掉进去过的坑
Makemigrations 后不执行 migrate,表没生成 很多人以为执行
makemigrations后就万事大吉,其实是生成 migration 文件,要运行migrate才会在数据库中实际建表。ForeignKey 引用 user 表时容易忘记导入 User 一开始我写了
assignee = models.ForeignKey('auth.User'),结果总是提示找不到User对象,后来改成从django.contrib.auth.models import User导入才解决问题。部署环境没有收集静态文件,页面样式丢失 生产环境下必须执行
collectstatic,才能让Nginx正确访问静态资源。数据库迁移冲突,尤其是 SQLite 换成 PostgreSQL 后的字段类型不符问题 建议一开始就在生产级数据库(如PostgreSQL)中测试,不然换数据库时可能会出现奇怪的字段转换错误。
接口设计:为未来留一条接口入口
虽然我们一开始是前后端混合开发的,但随着系统的扩展,我意识到有必要提供 REST API。于是我引入了 Django REST Framework,这一步后来成了关键决策。
安装方式:
pip install djangorestframework
添加到 INSTALLED_APPS:
INSTALLED_APPS += ['rest_framework']
然后就可以写一个简单的序列化器和服务端接口:
# tasks/serializers.py
from rest_framework import serializers
from .models import Task
class TaskSerializer(serializers.ModelSerializer):
class Meta:
model = Task
fields = '__all__'
# tasks/views.py
from rest_framework.decorators import api_view
from rest_framework.response import Response
from .models import Task
from .serializers import TaskSerializer
@api_view(['GET'])
def get_tasks(request):
tasks = Task.objects.all()
serializer = TaskSerializer(tasks, many=True)
return Response(serializer.data)
# tasks/urls.py
from django.urls import path
from .views import get_tasks
urlpatterns = [
path('api/tasks/', get_tasks, name='get_tasks'),
]
这样就可以用 /tasks/api/tasks/ 来获取JSON格式的任务数据了。后续我们就是靠这套API对接Vue前端,实现前后端分离架构。
上线部署:从开发走向生产
本地跑得欢不代表上线没问题。我们最初的部署是放在一台Ubuntu云服务器上的,用 Gunicorn + Nginx 做反向代理。
主要流程如下:
安装依赖:
pip install gunicorn psycopg2-binary修改 settings.py 中的数据库配置为 Postgres:
DATABASES = { 'default': { 'ENGINE': 'django.db.backends.postgresql', 'NAME': 'mydb', 'USER': 'myuser', 'PASSWORD': 'mypass', 'HOST': 'localhost', 'PORT': '', } }收集静态文件:
python manage.py collectstatic启动 Gunicorn 测试:
gunicorn taskmanager.wsgi配置 systemd 启动服务,避免重启服务器时进程消失
配置 Nginx 反向代理:
server { listen 80; server_name yourdomain.com; location /static/ { alias /path/to/static_root/; } location / { proxy_pass http://unix:/run/gunicorn.sock; } }
项目效果与反思总结

两个月过去,这个任务管理系统已经支撑了我们三个产品团队的需求流转。每天有几十条任务更新,用户反馈良好。虽然功能不算复杂,但稳定性一直不错。
回顾整个项目,我觉得有几点特别重要:
- Django 确实非常适合快速开发,尤其对于创业公司或者中小型项目,能让你尽快做出原型。
- 尽早规划模型关系很重要,否则后期改动成本很大。
- REST API 设计要提前考虑,即使一开始只做了模板渲染,后面也很可能需要接入前端框架。
- 不要怕犯错,多查文档,善用社区资源,很多你遇到的问题其实都有人踩过坑了。
给新手的一些建议
别迷信“完美开局”,边做边学才是正道 我也是从最基础的 Model、View、Template 开始,一路摸爬滚打过来的。只要你愿意动手,很快就能做出东西。
不要死磕源码,先搞懂基本流程 新手常有一个误区,非得搞清楚每个模块背后是怎么运作的。其实在初期更重要的是学会怎么用,而不是“为什么”。
多尝试部署,了解完整的交付流程 不要总停留在本地开发阶段,试着部署到一台 VPS 或者 Heroku 上,真实世界的调试会让你成长更快。
养成良好的 Git 提交习惯 我自己早期经常一改完就提交,也没有 message,后来出了 bug 想回滚都找不到版本。建议每次 commit 写清内容,分支管理也要规范。
结语
Django 是一个非常棒的框架,它不像 Node.js 那样灵活,也不像 Spring Boot 那么严谨,但它在“简洁高效”这件事上做得很好。尤其适合初创项目、内部工具、中小业务系统这类场景。
如果你正在学 Python,或者想找个框架来做 Web 项目,我强烈推荐你试一下 Django。它不仅帮你建立起一个网站,更教会你如何思考系统的结构、模型的设计、接口的设计……这些经验对你以后不管是转后端工程、DevOps 还是进入更大的体系都非常宝贵。
希望这篇实战笔记能够帮你在学习 Django 的路上少些迷茫,多些信心。共勉!

评论 0