1{
2 lib,
3 stdenv,
4 buildPythonPackage,
5 fetchFromGitHub,
6 fetchpatch,
7 pythonAtLeast,
8 pythonOlder,
9 replaceVars,
10
11 # build
12 setuptools,
13
14 # patched in
15 geos,
16 gdal,
17 withGdal ? false,
18
19 # propagates
20 asgiref,
21 sqlparse,
22
23 # extras
24 argon2-cffi,
25 bcrypt,
26
27 # tests
28 aiosmtpd,
29 docutils,
30 geoip2,
31 jinja2,
32 numpy,
33 pillow,
34 pylibmc,
35 pymemcache,
36 python,
37 pywatchman,
38 pyyaml,
39 pytz,
40 redis,
41 selenium,
42 tblib,
43 tzdata,
44}:
45
46buildPythonPackage rec {
47 pname = "django";
48 version = "4.2.23";
49 format = "pyproject";
50
51 disabled = pythonOlder "3.8";
52
53 src = fetchFromGitHub {
54 owner = "django";
55 repo = "django";
56 rev = "refs/tags/${version}";
57 hash = "sha256-h6VkMLg2XAVC0p+ItTs/2EqpYdZn9uNvv6ZwQHXP0bI=";
58 };
59
60 patches = [
61 (replaceVars ./django_4_set_zoneinfo_dir.patch {
62 zoneinfo = tzdata + "/share/zoneinfo";
63 })
64 # make sure the tests don't remove packages from our pythonpath
65 # and disable failing tests
66 ./django_4_tests.patch
67
68 # fix filename length limit tests on bcachefs
69 # FIXME: remove if ever backported
70 (fetchpatch {
71 url = "https://github.com/django/django/commit/12f4f95405c7857cbf2f4bf4d0261154aac31676.patch";
72 hash = "sha256-+K20/V8sh036Ox9U7CSPgfxue7f28Sdhr3MsB7erVOk=";
73 })
74
75 # backport fix for https://code.djangoproject.com/ticket/36056
76 # FIXME: remove if ever backported upstream
77 (fetchpatch {
78 url = "https://github.com/django/django/commit/ec0e784f91b551c654f0962431cc31091926792d.patch";
79 includes = [ "django/*" ]; # tests don't apply
80 hash = "sha256-8YwdOBNJq6+GNoxzdLyN9HEEIWRXGQk9YbyfPwYVkwU=";
81 })
82
83 ]
84 ++ lib.optionals (pythonAtLeast "3.13") [
85 # https://code.djangoproject.com/ticket/36499
86 # https://github.com/django/django/pull/19639
87 ./3.13.6-html-parser.patch
88 ]
89 ++ lib.optionals withGdal [
90 (replaceVars ./django_4_set_geos_gdal_lib.patch {
91 geos = geos;
92 gdal = gdal;
93 extension = stdenv.hostPlatform.extensions.sharedLibrary;
94 })
95 ];
96
97 postPatch = ''
98 substituteInPlace tests/utils_tests/test_autoreload.py \
99 --replace "/usr/bin/python" "${python.interpreter}"
100 ''
101 + lib.optionalString (pythonAtLeast "3.12" && stdenv.hostPlatform.system == "aarch64-linux") ''
102 # Test regression after xz was reverted from 5.6.0 to 5.4.6
103 # https://hydra.nixos.org/build/254630990
104 substituteInPlace tests/view_tests/tests/test_debug.py \
105 --replace-fail "test_files" "dont_test_files"
106 ''
107 + lib.optionalString (pythonAtLeast "3.13") ''
108 # Fixed CommandTypes.test_help_default_options_with_custom_arguments test on Python 3.13+.
109 # https://github.com/django/django/commit/3426a5c33c36266af42128ee9eca4921e68ea876
110 substituteInPlace tests/admin_scripts/tests.py --replace-fail \
111 "test_help_default_options_with_custom_arguments" \
112 "dont_test_help_default_options_with_custom_arguments"
113 '';
114
115 nativeBuildInputs = [ setuptools ];
116
117 propagatedBuildInputs = [
118 asgiref
119 sqlparse
120 ];
121
122 optional-dependencies = {
123 argon2 = [ argon2-cffi ];
124 bcrypt = [ bcrypt ];
125 };
126
127 nativeCheckInputs = [
128 # tests/requirements/py3.txt
129 aiosmtpd
130 docutils
131 geoip2
132 jinja2
133 numpy
134 pillow
135 pylibmc
136 pymemcache
137 pywatchman
138 pyyaml
139 pytz
140 redis
141 selenium
142 tblib
143 tzdata
144 ]
145 ++ lib.flatten (lib.attrValues optional-dependencies);
146
147 doCheck =
148 !stdenv.hostPlatform.isDarwin
149 # pywatchman depends on folly which does not support 32bits
150 && !stdenv.hostPlatform.is32bit;
151
152 preCheck = ''
153 # make sure the installed library gets imported
154 rm -rf django
155
156 # provide timezone data, works only on linux
157 export TZDIR=${tzdata}/${python.sitePackages}/tzdata/zoneinfo
158 '';
159
160 checkPhase = ''
161 runHook preCheck
162
163 pushd tests
164 ${python.interpreter} runtests.py --settings=test_sqlite
165 popd
166
167 runHook postCheck
168 '';
169
170 __darwinAllowLocalNetworking = true;
171
172 meta = with lib; {
173 changelog = "https://docs.djangoproject.com/en/${lib.versions.majorMinor version}/releases/${version}/";
174 description = "High-level Python Web framework that encourages rapid development and clean, pragmatic design";
175 mainProgram = "django-admin";
176 homepage = "https://www.djangoproject.com";
177 license = licenses.bsd3;
178 maintainers = with maintainers; [ hexa ];
179 };
180}