Django(ジャンゴ)は、Pythonで書かれたオープンソースのWebフレームワークです。データベース操作(ORM)、URLの振り分け、テンプレート、ログイン認証、管理画面までを本体に含むため、追加のライブラリを選ばなくても会員機能付きのWebアプリが組めます。この記事では、Djangoの標準機能、中核となるMVT(Model・View・Template)の仕組みとMVCとの違いを、Django 6.1.2で動かした最小アプリのコードと実行結果で説明します。2026年10月時点のサポート期限と、Djangoを選ばないほうがよい案件の条件もまとめました。
まとめ:Djangoの要点
- DjangoはPython製のフルスタックWebフレームワーク。ORM・管理画面・認証・CSRF対策などが本体に入っている。
- コードはModel(データ)・View(処理)・Template(表示)に分けて書く。MVCの「Controller」に当たるURLの振り分けはフレームワーク自身が受け持つ。
- 2026年10月時点の最新は6.1.2で、Python 3.12以上が必要。5.2 LTSは通常サポートが2025年12月3日に終わり、セキュリティとデータ消失の不具合修正が2028年4月まで続く。
- 新規開発は6.1で始め、2027年4月に出る6.2 LTSへ上げる計画にする。2028年からは年号の版(Django 2028)が毎年1月に出る。
- 非同期処理が主役のAPIや、エンドポイントが数本だけのサービスでは、Djangoの標準機能が重荷になる。
以下、定義と標準機能、MVTの仕組み、動かし方、版の選び方、向かない案件の順に説明します。
Djangoとは:PythonのフルスタックWebフレームワーク
Djangoは、米国カンザス州ローレンスの新聞社のWeb部門World Onlineで生まれました。Django公式FAQによると、2003年秋にAdrian HolovatyとSimon WillisonがPHPからPythonへ移り、地域サイトを作りながら汎用部分を抜き出して2年かけて育てたものを、2005年夏にオープンソースとして公開しました。締め切りの短いニュースサイトを次々に作る現場から出てきたため、公式サイトの標語も「The web framework for perfectionists with deadlines(締め切りのある完璧主義者のためのWebフレームワーク)」です。
ライセンスは3条項BSDライセンスで、商用でも無料で使え、改変・再配布もできます。開発は世界各地のボランティアのチームが担い、米国の501(c)(3)非営利団体Django Software Foundation(DSF)がスプリントやイベントの支援を通じて開発を後押ししています。
名前はジャズギタリストのジャンゴ・ラインハルト(Django Reinhardt)にちなみ、公式FAQは発音を「JANG-oh」、先頭のDは発音しないと説明しています。
Djangoに標準で入っている機能
Djangoを「フルスタック」と呼ぶのは、Webアプリで毎回作る部品が本体に入っているからです。django-admin startprojectで作った直後の設定ファイルには、管理画面・認証・セッションなど6つのアプリがすでに有効になっています。
| 機能 | Djangoでの名前 | 何が省けるか |
|---|---|---|
| データベース操作 | ORM・migrations | SQLの手書き、スキーマ変更の手作業 |
| 管理画面 | django.contrib.admin | 運用担当向けのデータ編集画面 |
| ログイン・権限 | django.contrib.auth | パスワードのハッシュ化、権限グループ |
| セッション | django.contrib.sessions | ログイン状態の保存 |
| 攻撃への防御 | CSRF・XSS・クリックジャッキング対策 | トークン検証やエスケープの自作 |
| CSP(6.0から) | ContentSecurityPolicyMiddleware | 外部パッケージの導入 |
実務で効くのは上の3つです。ORMはクラスでテーブルを定義し、makemigrationsで変更履歴を作ってmigrateで反映します。本番での適用順序と巻き戻しはDjango migrateの実務、管理画面の権限設計はDjango管理画面の設計、ログイン画面とカスタムユーザーの判断はDjangoのログイン機能の解説で扱っています。
標準のプロジェクト設定ではCSRF対策やテンプレートの自動エスケープなどが有効ですが、CSPはミドルウェアの追加とポリシー設定が必要です。これらを設定しても、すべての脆弱性を塞げるわけではありません。標準で防げる範囲とセキュリティリリースの追い方はDjangoの脆弱性への対応に整理しています。
MVT(Model・View・Template)の仕組み
Djangoのコードは、データを扱うModel、処理を決めるView、表示を組み立てるTemplateの3つに分けて書きます。日本語の解説ではMVTと書かれることが多いものの、公式FAQは「model」「template」「view」の順でMTVと呼んでいます。中身は同じです。
Model・View・Templateとファイルの対応
ModelとViewは、startappで生成されるファイルに記述します。TemplateのディレクトリとHTMLファイルは自分で作成します。どこに何を書くかが決まっているので、他人のDjangoプロジェクトでも処理の場所をすぐに探せます。
| 役割 | 書くファイル | 担当すること |
|---|---|---|
| Model | models.py | テーブルの定義、データの読み書き |
| View | views.py | どのデータをどのテンプレートに渡すか |
| Template | templates/アプリ名/*.html | データをどう見せるか |
| (URLの振り分け) | urls.py | URLとViewの対応表 |
通常の具象Modelでは1クラスが1つのテーブルに対応し、モデルフィールドが列に対応します。抽象モデルやプロキシモデルは、それ自体のテーブルを作りません。Viewは関数かクラスで書き、リクエストを受けてレスポンスを返します。Templateは{{ 変数 }}と{% for %}などのタグでHTMLにデータを埋め込みます。検索条件や業務上の計算はModelやView側に置きますが、テンプレート内でQuerySetを反復するとSQLが発行される場合があります。テンプレートの継承やJavaScriptへの値渡しはDjangoテンプレートの書き方、QuerySetがいつSQLを発行するかはDjango ORMのクエリ設計で詳しく扱っています。
1つのリクエストが処理される順番
ブラウザが/を開くと、Djangoは次の順で処理します。
- URLディスパッチャが
urls.pyのurlpatternsを上から照合し、一致したViewを呼ぶ。 - ViewがModel経由で検索条件を指定する。QuerySetは遅延評価されるため、掲載例ではテンプレートが記事を反復するときにSQLが発行される。
- Viewが
render()でテンプレートにデータを渡し、HTMLを組み立てる。 - 組み立てたHTMLをHTTPレスポンスとして返す。ミドルウェアはViewの前後に処理を行い、セッションの準備やCSRF検証はViewが呼ばれる前に行う。
アプリ固有の処理を追う起点はViewですが、ミドルウェアが先に応答してViewが呼ばれない場合もあります。不具合を追うときは、URLからurls.pyを引き、対応するViewを読むところから始めれば迷いません。
MVCとの違い:コントローラはフレームワーク自身
MVC(Model・View・Controller)と比べると名前がずれています。MVCの「View(表示)」に当たるのがDjangoのTemplate、MVCの「Controller(制御)」に近いのがDjangoのViewです。
公式FAQはこの点を次のように説明しています。Djangoの「view」はどのデータを見せるかを決め、どう見せるかはtemplateに任せる。では「controller」はどこにあるのかといえば、「おそらくフレームワーク自体(probably the framework itself)」、つまりURL設定に従ってリクエストを適切なviewへ送る仕組みだ、という説明です。開発者がルーティング用のControllerクラスを書かず、urls.pyに対応表を書くだけで済むのはこのためです。
Rails・Laravel・Spring MVCなどのMVCフレームワークから移る人は、「Controllerに書いていた処理はviews.pyに書く」と置き換えると早く慣れます。MVCという設計そのものが今も使われている理由はMVCモデルが2026年も現役である理由で解説しています。
Djangoで最小のアプリを動かす手順
ここからは、記事の一覧を表示するだけのアプリでMVTの3ファイルを1つずつ書きます。以下のコードと出力は、macOS上のPython 3.13とDjango 6.1.2で実行したものです。Django 6.1はPython 3.12以上を要求するため、3.11以前のPythonではpip installで6.1が入りません。
インストールとプロジェクトの作成
仮想環境を作り、版を固定してインストールします。startprojectの最後の.は、今いるフォルダにプロジェクトを作る指定です。
python3 -m venv .venv
source .venv/bin/activate
python -m pip install "Django==6.1.2"
python -m django --version
# 6.1.2
django-admin startproject mysite .
python manage.py startapp blog
この2つのコマンドで、次のファイルが作られます。mysiteがプロジェクト全体の設定、blogがアプリ1つ分です。
manage.py
mysite/ __init__.py settings.py urls.py asgi.py wsgi.py
blog/ __init__.py admin.py apps.py models.py tests.py views.py
blog/migrations/__init__.py
作ったアプリはmysite/settings.pyのINSTALLED_APPSの末尾に"blog"を足して有効にします。日付を日本語で出すために、同じファイルのLANGUAGE_CODEを"ja"、TIME_ZONEを"Asia/Tokyo"に変えておきます。
6.1のsettings.pyにはDEFAULT_AUTO_FIELDの行がありません。指定しなくても主キーは64ビットのBigAutoFieldになり、下のModelでもBigAutoFieldが使われました。
記事一覧のModel・View・Templateの実装
まずModelです。記事のタイトルと公開日の2列を持つテーブルを定義します。
# blog/models.py
from django.db import models
class Article(models.Model):
title = models.CharField(max_length=200)
published = models.DateField()
def __str__(self):
return self.title
次にViewです。新しい順に記事を取り出し、テンプレートにarticlesという名前で渡します。
# blog/views.py
from django.shortcuts import render
from .models import Article
def article_list(request):
articles = Article.objects.order_by("-published")
return render(request, "blog/article_list.html", {"articles": articles})
Templateはblog/templates/blog/article_list.htmlに置きます。アプリ名のフォルダを1段挟むのは、別のアプリにある同名のテンプレートとぶつからないようにするためです。
<ul>
{% for a in articles %}
<li>{{ a.published }} {{ a.title }}</li>
{% empty %}
<li>記事はまだありません</li>
{% endfor %}
</ul>
最後に、URLとViewを結びます。ここが公式FAQのいう「controller」の役割です。
# mysite/urls.py
from django.contrib import admin
from django.urls import path
from blog.views import article_list
urlpatterns = [
path("admin/", admin.site.urls),
path("", article_list),
]
マイグレーションと実行結果
Modelからテーブルを作ります。makemigrationsが変更履歴のファイルを作り、migrateがそれをデータベースに当てます。
python manage.py makemigrations blog
# blog/migrations/0001_initial.py
# + Create model Article
python manage.py migrate
# Applying blog.0001_initial... OK ほか、計19件
19件のうち18件は、管理画面・認証・セッションなど標準アプリのマイグレーションです。テーブル作成だけでなく、既存の定義やデータを変更する処理も含まれます。設定を何も書かなくても、SQLiteのファイルdb.sqlite3にユーザーやセッションのテーブルが用意されます。
データを2件入れて/を開き、発行されたSQLも数えます。manage.py shellに次のコードを流しました。
import datetime
from django.db import connection
from django.test import Client
from django.test.utils import CaptureQueriesContext
from blog.models import Article
Article.objects.create(title="Django 6.1 リリース", published=datetime.date(2026, 8, 5))
Article.objects.create(title="Django 6.1.2 セキュリティ修正", published=datetime.date(2026, 10, 6))
with CaptureQueriesContext(connection) as ctx:
res = Client().get("/", HTTP_HOST="localhost")
print(res.status_code)
print(res.content.decode())
print(len(ctx.captured_queries), ctx.captured_queries[0]["sql"])
200
<ul>
<li>2026年10月6日 Django 6.1.2 セキュリティ修正</li>
<li>2026年8月5日 Django 6.1 リリース</li>
</ul>
1 SELECT "blog_article"."id", "blog_article"."title", "blog_article"."published" FROM "blog_article" ORDER BY "blog_article"."published" DESC
Viewのorder_by("-published")は、ORDER BY ... DESC付きのSQL 1本になりました。日付はLANGUAGE_CODE = "ja"の設定で「2026年10月6日」と表示されます。en-usのままだと「Oct. 6, 2026」です。
HTTP_HOST="localhost"を外すと、テスト用クライアントが送るホスト名testserverがALLOWED_HOSTSに無いため、ステータス400(DisallowedHost)になります。DEBUG = TrueでALLOWED_HOSTSが空のとき、Djangoが受け付けるのはlocalhostとそのサブドメイン、127.0.0.1、[::1]だけです(ALLOWED_HOSTSの公式説明)。
ブラウザで確認するならpython manage.py runserverを起動してhttp://127.0.0.1:8000/を開きます。開発用サーバーなので本番では使いません。gunicorn+nginxの本番構成はDjangoのデプロイ手順で説明しています。
管理画面へのArticleモデルの登録
blog/admin.pyに2行足すだけで、Articleの一覧・追加・編集・削除の画面ができます。
# blog/admin.py
from django.contrib import admin
from .models import Article
admin.site.register(Article)
python manage.py createsuperuser
ログインしていない状態で/admin/を開くと、ステータス302で/admin/login/?next=/admin/へ転送されました。作った管理ユーザーでログインすると、Articleを登録した画面が表示されます。この先、投票アプリを作りながらフォームやテストまで進むなら、公式のはじめての Django アプリ作成(その1〜その8)が日本語で読めます。
Djangoのバージョンとサポート期限(2026年10月時点)
公式ダウンロードページの表では、2026年10月28日時点でサポート中の系列は次の3つです。Pythonの対応は公式のインストールFAQによります。
| 系列 | 最新 | 通常サポート終了 | 延長サポート終了 | 対応Python |
|---|---|---|---|---|
| 6.1 | 6.1.2 | 2027年4月 | 2027年12月 | 3.12〜3.14 |
| 6.0 | 6.0.9 | 2026年8月4日 | 2027年4月 | 3.12〜3.14 |
| 5.2 LTS | 5.2.18 | 2025年12月3日 | 2028年4月 | 3.10〜3.14 |
| 6.2 LTS(予定) | 2027年4月公開 | 2027年12月 | 2030年4月 | – |
表の注記によると、通常サポート中はセキュリティ修正に加えて、データ消失・クラッシュ・新機能の重大な不具合・旧版からの退行も直ります。延長サポートで直るのは、セキュリティとデータ消失の不具合だけです。4.2 LTSは2026年4月7日で延長サポートも終わりました。6.1のPython 3.15対応は、6.1.3から加わると公式FAQに書かれています。
新規開発で選ぶ版
いまから作るなら6.1です。「本番はLTS」という以前の定石に従って5.2 LTSを選ぶと、すでに通常サポートが終わった版で開発を始めることになります。6.1の延長サポートは2027年12月までなので、2027年4月に出る6.2 LTSへ上げる作業を最初から予定に入れておきます。
5.2 LTSは、Python 3.10・3.11や依存パッケージの互換性に制約がある場合、または2028年4月までの延長サポートを前提に保守する場合の選択肢です。通常の不具合修正が対象外である点を踏まえて判断します。6.0のリリースノートは、Python 3.10と3.11に対応するのは5.2系が最後だと明記しています。旧版からの移行順序や、各版のPython対応の細かい組み合わせはDjangoのEOLとサポート期限一覧にまとめています。
2028年からの年号の版
Djangoは6.2を最後に版番号の付け方を変えます。6.1のリリースノートによると、7.0・7.1として予定していた版はDjango 2028・Django 2029になり、以後は毎年1月に年号の版が出ます。パッチは2028.3のような形です。
サポートの考え方も変わります。これまでは約8か月ごとの機能リリースのうちLTSだけが3年サポートでしたが、Django 2028からはすべての機能リリースが同じ3年のサポートを受けます。公式表ではDjango 2028の通常サポートが2029年1月、延長サポートが2031年1月までです。LTSが出るのを待って上げる運用は要らなくなり、毎年1回上げるか、3年以内に次へ移るかを選べます。
6.0と6.1で標準に入った機能
以前は外部パッケージで足していた機能のいくつかが、6.0と6.1で本体に入りました。
- CSP(6.0):
ContentSecurityPolicyMiddlewareとSECURE_CSP設定でContent Security Policyのヘッダーを付けられる。 - テンプレートの部品化(6.0):
{% partialdef %}と{% partial %}で、1つのテンプレートファイルの中に名前付きの断片を定義して使い回せる。 - Tasksフレームワーク(6.0):
@taskでバックグラウンド処理を定義し、enqueue()でキューへ積める。ただし処理を実行するワーカーは本体に含まれず、外部のワーカーが必要。 - fetch mode(6.1):取得していない項目に触れたときの読み込み方を
QuerySet.fetch_mode()で選べる。 - データベース側の削除(6.1):
on_deleteにDB_CASCADEなどを指定すると、削除の連鎖をSQLのON DELETEに任せられる。
fetch modeはN+1問題に直接効きます。著者を外部キーに持つ本10件をループして著者名を読むと、既定のFETCH_ONEではSQLが11本、FETCH_PEERSでは2本でした。FETCH_RAISEにすると、その場でFieldFetchBlocked例外が出て、意図しないSQLの発行を止められます。N+1問題そのものと検出方法はN+1問題の実測と対策、DB_CASCADEなどの選び方はDjango on_deleteの選び方で扱っています。
Tasksは、定義とキュー投入の書き方がそろっただけで、実行には外部のワーカーが要ります。いま本番でバックグラウンド処理を回すなら、分散タスクキューのCeleryのような専用の仕組みを組み合わせます。
Djangoのメリットと向かない案件
Djangoを選ぶ理由ははっきりしています。管理画面・ログイン・権限・データベースの土台を自分で組まずに済むことです。業務システム、会員制サイト、社内の管理ツールのように、データの登録と閲覧の画面が多く、運用担当が中身を直す案件ほど効きます。公式FAQには、Disqus・Instagram・Pinterest・Mozillaが長年使い、毎秒5万ヒットを超えるアクセスの急増にも耐えたサイトがあると書かれています。Instagramについては、Metaが2023年8月の技術ブログで、フロントエンドのサーバーにPythonのDjangoを使っていると説明しています。
業務システムをDjangoで作るか、要件から作り方を決めたい場合は、弊社のフルスクラッチ開発で設計から相談を受けています。Djangoで作られたサービスの類型と、見積もりへの影響はDjangoで作られたWebアプリの例にまとめました。
Djangoを選ばないほうがよい条件
次のどれかに当てはまる案件では、Djangoを第一候補にしません。
- 非同期処理が主役で、トランザクションも要る:Djangoはasync viewとASGIに対応し、ORMにも
acreate()などの非同期版がある。ただし公式ドキュメントは、非同期モードではトランザクションがまだ動かないと明記しており、トランザクションが要る処理は同期関数にまとめてsync_to_async()で呼ぶ必要がある。外部APIを大量に並行で呼ぶ処理が中心なら、最初から非同期前提のFastAPIのほうが書く量が少ない。 - JSONを返すエンドポイントが数本だけ:管理画面も会員機能も使わない小規模APIでは、Flaskなども比較対象にする。Djangoでも不要な標準アプリは外せるため、初期状態のマイグレーション数だけで採否を決めない。
- Python 3.11以前から上げられない:6.x系が入らず、通常サポートの終わった5.2で始めることになる。
学習の負担も軽くはありません。ORM・マイグレーション・テンプレート・認証・設定ファイルの約束事を一通り覚えるまでは、Flaskより手数が多く感じます。FastAPIとの違いはFastAPIの解説、Flaskとの選び方はDjangoとFlaskの違い、求人や採用状況の数字から見た将来性はDjangoの将来性の記事で扱っています。
DjangoでAPI・リアルタイム通信を作るときの選択肢
Django単体でもJSONは返せますが、REST APIを本格的に作るなら専用のパッケージを足すのが普通です。
- 認証・権限・ページングまでそろえたREST APIを作る:Django REST Framework(DRF)。入出力の変換はDRFのSerializerが担う。
- 型ヒントでスキーマを書き、非同期のAPIを軽く作る:Django Ninja。
- 画面をReactで作り、DjangoをAPIサーバーにする:ReactとDjangoの連携方法(CORS・JWT認証)。
- チャットや通知などWebSocketが要る:Django Channels。
画面のあるWebアプリならDjango本体のテンプレート、APIだけならDRFから始めます。どちらも日本語の情報が多く、つまずいたときに調べやすい組み合わせです。
よくある質問
Djangoの読み方は?
「ジャンゴ」と読みます。公式FAQの発音表記は「JANG-oh」で、先頭のDは発音しません。名前はジャズギタリストのジャンゴ・ラインハルトに由来します。
Djangoは無料で商用利用できますか?
できます。Djangoは3条項BSDライセンスで配布されており、商用利用や改変・再配布にライセンス料はかかりません。ただし、再配布時の著作権表示・ライセンス条件・免責条項の保持など、ライセンスの条件を守る必要があります。
DjangoはMVTとMTVのどちらが正しいですか?
指しているものは同じです。公式FAQは「model」「template」「view」の順でMTVと書いており、日本語の解説ではMVTと書かれることが多くなっています。どちらの呼び方でも、Model・View・Templateに処理を分ける設計を指します。
DjangoはフロントエンドとバックエンドのどちらのWebフレームワークですか?
サーバー側で動くバックエンドのフレームワークです。ただしテンプレート機能でHTMLも組み立てるため、画面まで含めたWebアプリをDjangoだけで作れます。画面をReactやVueで作る場合は、DjangoはAPIを返す側に回ります。
Djangoを使うにはPythonのどの版が必要ですか?
2026年10月時点の最新版Django 6.1.2は、Python 3.12・3.13・3.14に対応しています。PyPIの登録情報もPython 3.12以上を要求しており、3.11以前の環境では5.2系までしか入りません。