diff options
author | Ian Delaney <idella4@gentoo.org> | 2014-09-14 05:43:04 +0000 |
---|---|---|
committer | Ian Delaney <idella4@gentoo.org> | 2014-09-14 05:43:04 +0000 |
commit | e3a075173f92a57e8f1ffb2b09c9e80d8cb2c530 (patch) | |
tree | 0597e569f812d82d9404aacd76e2b4d6fef45c11 /dev-python/django | |
parent | version bump (diff) | |
download | historical-e3a075173f92a57e8f1ffb2b09c9e80d8cb2c530.tar.gz historical-e3a075173f92a57e8f1ffb2b09c9e80d8cb2c530.tar.bz2 historical-e3a075173f92a57e8f1ffb2b09c9e80d8cb2c530.zip |
bump; upgrade deps, tidy test phase
Package-Manager: portage-2.2.10/cvs/Linux x86_64
Manifest-Sign-Key: 0xB8072B0D
Diffstat (limited to 'dev-python/django')
-rw-r--r-- | dev-python/django/ChangeLog | 8 | ||||
-rw-r--r-- | dev-python/django/Manifest | 23 | ||||
-rw-r--r-- | dev-python/django/django-1.7.ebuild | 94 | ||||
-rw-r--r-- | dev-python/django/files/1.7-test_serialize.patch | 507 |
4 files changed, 616 insertions, 16 deletions
diff --git a/dev-python/django/ChangeLog b/dev-python/django/ChangeLog index 844a5884c7e4..838405d1ac0e 100644 --- a/dev-python/django/ChangeLog +++ b/dev-python/django/ChangeLog @@ -1,6 +1,12 @@ # ChangeLog for dev-python/django # Copyright 1999-2014 Gentoo Foundation; Distributed under the GPL v2 -# $Header: /var/cvsroot/gentoo-x86/dev-python/django/ChangeLog,v 1.144 2014/09/13 17:24:49 ago Exp $ +# $Header: /var/cvsroot/gentoo-x86/dev-python/django/ChangeLog,v 1.145 2014/09/14 05:42:33 idella4 Exp $ + +*django-1.7 (14 Sep 2014) + + 14 Sep 2014; Ian Delaney <idella4@gentoo.org> +django-1.7.ebuild, + +files/1.7-test_serialize.patch: + bump; upgrade deps, tidy test phase 13 Sep 2014; Agostino Sarubbo <ago@gentoo.org> django-1.4.15.ebuild, django-1.5.10.ebuild, django-1.6.7.ebuild: diff --git a/dev-python/django/Manifest b/dev-python/django/Manifest index 4edf5a7d3153..69d44ffb4dd8 100644 --- a/dev-python/django/Manifest +++ b/dev-python/django/Manifest @@ -1,6 +1,7 @@ -----BEGIN PGP SIGNED MESSAGE----- Hash: SHA256 +AUX 1.7-test_serialize.patch 21251 SHA256 85cfe51ba76d8d200b233d8d3db4b07dd84b1f58e615329eda388b989d4e5375 SHA512 f737d8c648da696a6022ef5007cc1ab9a94c0627593fdc9b21e9588c2a83d151887f8483731c9388d807829c5f763451c4bd25a45519551c445c10457ec8bf17 WHIRLPOOL 56b093733382ceb8c056d9edf30bfb4a423f71dff54956ca8345d744fc9f8bf6293e67b7f66b6ff81a058471453a84e31fa907f7270212a2f190b9673605abb6 AUX django-1.5-objects.patch 1470 SHA256 6b0ce991c1b9c97d642faf9f5aa554796c2fdec52cc0f78b6447626a4f9f6816 SHA512 c82592ba39b121111c86d8713a24e6120a27991e057f9c034722e2054ff51a09e4cdce997a9059245a602c9343ab8b8930e14cb36cfd088da2b5e44e11d13cc4 WHIRLPOOL 84bd83ae54f8cd62dec2973e064511814205789fd8031fb6ad142bf0e865f4af32e34dfcb1bf82476a2e0e58df75ed6424d646fc618c353dedf8015f0c2bdb70 AUX django-1.5-py3tests.patch 959 SHA256 62fbb00c8d919306b48c8fcc82c7fa5e8aa38589f5271c526757da0ff2acbaa7 SHA512 cc746d43c2cc1c7f88fbffbf07ffc1f3b3fdcb738547658623c763e302c69372f8c8c014ac2a7196382d21aee0ba2ede92860a59a76ad3e14541015969935a92 WHIRLPOOL 4da24b4006ff233fea8041127a2842485d7d178d5abba2b429f537a66feb21384a59678188451089429af355118f06fc7083cbdd61d12905f9dfdb4e831d668b AUX django-1.5.4-objects.patch 1467 SHA256 237d0ee4e9f2af1d98b0b230977a41d061cbdbefc153193bc1539c4ad82622ee SHA512 09bdaab452f692679a15d0fbadf3c044417aeda0ce65b30bd2994d86b33ae93c13eb159fdad373a031ab2e0563861e29d1f9935b52c33af34a6afd25461e904d WHIRLPOOL d8a18947bd826c28836ce5180a6f9de758722fcc45ba11ca6a887c65711e7fa23827dcab734b6bfe51c330dd05a2d67a5d82e6e2d85130cdb05fcb4ca0622f26 @@ -11,29 +12,21 @@ DIST Django-1.5.10.tar.gz 8074324 SHA256 7cb4217e740f7d5d6d74617dbb9d960f9c09e82 DIST Django-1.5.9.tar.gz 8074400 SHA256 47ce505c5046c38817828bee253b7256872f86c4340db1af698cb8548dbaa0d2 SHA512 0b42f09a6bd28b18eaaf6b1788fcc620ee410442c4f179130babed3fa6763155cc5469e1b38d68a87742a21f34e0ac343167dd7a9de0595c81e81a25296a1087 WHIRLPOOL 817e88b2a82b48d6c7f2f78091f66b786227b5513be01f99c90a5ab36920e5d15167dc209e9954641d61536e62e396719224fbd4b5812e349ccf59e48ff1d72b DIST Django-1.6.6.tar.gz 6645456 SHA256 536cbd54e533ba3563d205f0c91988b24e7d74b8b253d7825e42214b50ba7e90 SHA512 4d52ed7e31df7d1b449697e5ecd48a94cbb365a1f0abe6b9308ba815b1ef80d2c38d8ba07a57f928617a592afaa44d48374ecf3901b66e68d389fc4ac4f6891d WHIRLPOOL db69860de31c2283faab0931818d215dab12cb36ed1f8b3160d0e1b5ed49c72b66b751b086cd454acde76c5c1b003ca89fabbdf88603de7b4cacf5df4385d3e0 DIST Django-1.6.7.tar.gz 6647301 SHA256 9a64211c96a3262bb2545acc82af5d8f3da0175299f7c7e901e4ed455be965fb SHA512 7806562853c1c2db1decc597ec62f1e91689a6a3668030ed8dc0a757e5bf1603f4be945cef277ce564d26665a39d5c4151060b7889822e66671345d973dd256d WHIRLPOOL 6cbac5dbea4a37e88beeec3402ce264fdc889fcc6ec319fdc7436b45a538ad9a4ccb4fc01bf4c122407700e7cf6f8223bd40aa94af16bfa801dc93aa46576484 +DIST Django-1.7.tar.gz 7486550 SHA256 33f781f17f145f79ee8e0b8d753498e0e0188f0b53b2accad4045d623422d5e1 SHA512 9eb96812b913372f2e95e70fb498109d42d74a7df2a8b26083c5b372b421d897ef4119f45bfeb1cf2ef224448e9e0cfb801842441454b9b16c524e94d80d509a WHIRLPOOL a462e153501e572ef00c4319165b953ab3658d2bf1250eae05b75b8ff3ade0621b1a58943ac1fee4441c239cb3384e2ee73764c8255090a7a419675d09c19260 EBUILD django-1.4.14.ebuild 2557 SHA256 c9b15a402c64e4faca76c8fbf6dfce82337dc182ca7ce153e546b95e91eea17f SHA512 ddf443a02963a5ad6decfa2695bfdb824ab1b107adddff2fb6f063de7b3a0ec16c837792a180da47b89ab3a2237ec58423eba68a53de3bf7bd92e04187fdbdaf WHIRLPOOL a7c53d1deeace93ec1f7ce9450c50ca2add66b64842f19121c25610d9909de69c40cf8f40294fbb892da8a0c658709d09e1a183438767d4252cd391c329dc63a EBUILD django-1.4.15.ebuild 2557 SHA256 7248e0267a58f4b5a35fe2d7d4b164750921f0bccc2260bc572c23dc0a8894c2 SHA512 58380a2443d8966ff78616ff4a90645cca4cf0e1cf672077b928542931b96230caa85dbf395ae4e0af80aa962383167885a9cb1779d3cab96ccc1d3e5998742a WHIRLPOOL 8792466779f3e249ae584d32bb54f42dc990558b26b288129024b6e66e5b06c23cbed04d922c06e73b7067f6ee8fcbbe86e8ebc82dc0976811f32bef984c4640 EBUILD django-1.5.10.ebuild 2570 SHA256 4516728575bf4f4386d18ff8b7b3dfc528988a2613314ed652cbaefaac85ee87 SHA512 81c02f0e126ba9c193bce65e06b51a903f927f1b313b34b789b48e6f70ee09bfee38821fe607597e240726fc5d5a9e47a50dd6d2c60ccdd2d22aef5c9da8207d WHIRLPOOL 9cd10f6cf0686cacbc1f74c22a3bbdd66aecb7db7484f392e2b643e322bfac65b34af4fbb631734ba8f62efdf5cb52f8841a56188f072fc3f808cfe5e2430c86 EBUILD django-1.5.9.ebuild 2569 SHA256 b735074b0aadcab45b759fb0657d0a5304e6d2f17297aec824ef6107de5dd33c SHA512 ca0c262ed213b76bd756f669db4b0014a75b82d5c82b9296b4badf3ca6ffee5dd2d47679f0852f705a187ff675d2bfe7b623ee4730362ef8a5e556f60343c2f1 WHIRLPOOL 4b63d45f100b36769ae9f95c517efdb6f3c2ca0a4a81f6a876e89da26dbe5af97ec6a9777d856e58b03a4e4aa765593c2aa811820bb3907fa58be74c30769e5d EBUILD django-1.6.6.ebuild 2684 SHA256 3c8b388d16b86e1f9c626bfeb530eede945e11db23803b5ae78a13af53d9022e SHA512 1245ea8a5818523af6386897eb9abb0b234243c9123f885f8d17b3063a200b6abb475106f770870a23df4f740f76edf1c152d8dfc72c18447abc6d9e2d2b80a6 WHIRLPOOL a365f416c1d744374559dbf2db293341d4f2125ea0d520853c26a381f3a4100b2c49eeda969ee4601be474c200fd380a59f5ecd14712d88b100242f20c1ff56f EBUILD django-1.6.7.ebuild 2684 SHA256 ac20d60450edf0d1435cefd2c32fe3f0d0149ccefc84ddd8c43f353bd6a3ece2 SHA512 7db7b9fabb5fce54c6671080aa9f05ae905bd16cb464ae7c34314bb7b91775389b42a7ca49fe217434b097b9cf8c8ec877c99da154358e78b6c920f7106f2756 WHIRLPOOL 340f26362d206e21ce2180c6c52b554a0d21000de9e7e285a6504462e81098db3372dc643f98d5a657e95f6f1b6f6b0c333c584644eef4e592e065014f284a90 +EBUILD django-1.7.ebuild 2766 SHA256 e663f2ba8f07ca83bc6549feedd70604ccd5aeb3215fac9bf10a8a4945ebf63d SHA512 b569fa219680d9bad6a5c9b1145f2508ee55afc09dc698068381bf13dad90f8e827cde13a215a09abbaef29a631a6e1148a884b1b9f639d11028e8a113b10f00 WHIRLPOOL e49e69de1747120e25e8f8d8de716b9cf29f6df68945595b341d0694cf12ca8a8ff0ef9a832216a1c495413d938e403e2d915fbf64e764b3e0c8377e24ce1249 EBUILD django-9999.ebuild 2378 SHA256 53f3f83d91d9fba975d5ee353a91b9ecadb874b2da551b234baeed7747bfae20 SHA512 521cac5140c8ddd2529c9a103ded73427e83a1107804639090cbfb186a7a691aa49c02587fa06081218960f9e34c6b971e4dc2805d160e6c2b775c3c7498afc1 WHIRLPOOL 892b0145749a5446b4b75ee41045795ddd63459d5c0024657d7477c02c8f3c32fafdab8a5e586e623f26c9554fb98a69525ba00e5c43a5e0cdfd6149fa348f86 -MISC ChangeLog 22441 SHA256 df7434bac60148823c75a0213cf6eb17ae49c2f086bfd895e38add80ee8ce703 SHA512 7d2890c889da35d959c66cebbb53248fa46a66429f4c5ee5282856e8c02496c98f32dbf0db26af077c7edd3eb608a70362ac8c3bd8bda8169fab02d466e6140b WHIRLPOOL 525d84225beabbc13d738e3d5bee3d39835d0f2dd6017f4655dfcf97fd70cd8369178f81416d8722debcab886f272b94e2ca448b487e053ada6f78cea3454a1e +MISC ChangeLog 22614 SHA256 99ed7e60bf51cdd5b1cab197ea8499f59bba1ab91043158458a2c8a91d369aef SHA512 f3a2080bf973047ded3c4b2ab29e2c3821d0cdcc81b6a48dd4b8af7433e7f3c240003180a364ad193bfdaf98a96629a533e83f67e54d3d684eea1b62a17a4d07 WHIRLPOOL 696727f56f17cb8c6e07e1f43ad75e80a4bbda3d3601168ac1f719f5ee7738b6b004bf99ed9449dff8ee518666acb076fe6f9803f2aa457d1f0c532c6d3f4e00 MISC metadata.xml 160 SHA256 6cd954a9de2307c57d32b25fa3599dee2908a4ddc6a98594f593d53577307a3a SHA512 7c02a1de1ddcb6b7c6378cceff0458da3a15d5381417f7cdf01874e7c372664b8899863f41b3a2fd8d6ad67ceb732dac6da0cc17575bf8e3e6d89480417c6628 WHIRLPOOL ed2795e4466eda8c804d5067c87386e269a59fe959393057ca5ddc36851e00f5210c4da1adf4bbdfdbb7d1d3d5c60aced25727ca12fdc8305d9e263a3aca9b13 -----BEGIN PGP SIGNATURE----- -Version: GnuPG v2 +Version: GnuPG v2.0.22 (GNU/Linux) -iQIcBAEBCAAGBQJUFH3jAAoJELp701BxlEWfCAcQAIQmHwx4ye4RDD8rchF8Qa3V -G8RfTO68trrA/IbtaeKe8x2K6AAEUO0cJIeRhILqW+27U3LAMkm0Q8c+ulOgyrBe -czqDwLIh5FyBu0VzJYBChAVjvo5A5VhrO3NcZrfCejSybYdq71XMdBgQqW95Z5Es -1FSlzRhI8M1z7BAsN29YeI2TC9HWfFTCTr7skgEX9r9sTJShCfUz2o3vPTY5ikbc -s35HfWEgPOqHl10kOJgsAGV02uk8E0M7WMnGMQ4XORPZPybYyzjrIvJ2/iIbpBX0 -Kjheael6MDIBfiNoPtVQaIbQdHLJalNfYs6M/Ar/JwCvtrlakp8OenusEZdtmsk8 -0HjNpk0jyQbzvLOvxzrrO7hR7Jlh6/uiNJwe/Lhi2aD8GEH7XQ6ZO99I+u9Cqy9i -ii3lbOlsUTkTSfYNiYsfHIzOAr4IkHe8tBMbzO+m4kbjUHqlqjiqgA2+4LN0OipD -3vz6jtXNICBzWOZU5QqMYg2yyQmKVThddQWgFBFXQb3rieHZuEAsJAQyXNuxCyCH -mAfPeKsZsR4fo3AfUSeaqm28j4FkIsutVRQgt17oGZOrbDeQDY+v7UvR4YDHqNMZ -0mhLR/a3DQUZpQgtDH9ieqmRiBc0zmW/WeopZ/0Zqqgaw3101Vb6btBP+RElXAUP -c4eXqMKojzTxVLFcJul4 -=dGg8 +iEYEAREIAAYFAlQVKJ4ACgkQso7CE7gHKw05tQCeN6FlqUvoJbnzrVts3QVpcVxg +OnMAoJOjq0/WaMMCKBGR+o8JWd5m/NH/ +=+14j -----END PGP SIGNATURE----- diff --git a/dev-python/django/django-1.7.ebuild b/dev-python/django/django-1.7.ebuild new file mode 100644 index 000000000000..135776db8836 --- /dev/null +++ b/dev-python/django/django-1.7.ebuild @@ -0,0 +1,94 @@ +# Copyright 1999-2014 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Header: /var/cvsroot/gentoo-x86/dev-python/django/django-1.7.ebuild,v 1.1 2014/09/14 05:42:33 idella4 Exp $ + +EAPI=5 +PYTHON_COMPAT=( python{2_7,3_3,3_4} pypy ) +PYTHON_REQ_USE='sqlite?' +WEBAPP_NO_AUTO_INSTALL="yes" + +inherit bash-completion-r1 distutils-r1 versionator webapp + +MY_P="Django-${PV}" + +DESCRIPTION="High-level Python web framework" +HOMEPAGE="http://www.djangoproject.com/ http://pypi.python.org/pypi/Django" +SRC_URI="https://www.djangoproject.com/m/releases/$(get_version_component_range 1-2)/${MY_P}.tar.gz" + +LICENSE="BSD" +SLOT="0" +KEYWORDS="~amd64 ~ia64 ~ppc ~ppc64 ~sparc ~x86 ~x86-fbsd ~amd64-linux ~x86-linux ~ppc-macos ~x64-macos ~x86-macos" +IUSE="doc mysql postgres sqlite test" + +RDEPEND="virtual/python-imaging[${PYTHON_USEDEP}] + dev-python/setuptools[${PYTHON_USEDEP}] + postgres? ( $(python_gen_cond_dep 'dev-python/psycopg:2[${PYTHON_USEDEP}]' python2_7 'python{3_3,3_4}') ) + mysql? ( $(python_gen_cond_dep '>=dev-python/mysql-python-1.2.3[${PYTHON_USEDEP}]' python2_7) )" +DEPEND="${RDEPEND} + doc? ( >=dev-python/sphinx-1.0.7[${PYTHON_USEDEP}] ) + test? ( ${PYTHON_DEPS//sqlite?/sqlite} )" + +S="${WORKDIR}/${MY_P}" + +WEBAPP_MANUAL_SLOT="yes" + +pkg_setup() { + webapp_pkg_setup +} + +python_prepare_all() { + # https://github.com/django/django/commit/d0c6016367c11d4d4cc42ace340f951f5b75738e + # Courtesy of Arfrever + sed -e "106a\\ with change_cwd(\"..\"):" \ + -e "107,117s/^/ /" \ + -i tests/test_runner/test_discover_runner.py + + # Prevent d'loading in the doc build + sed -e '/^ "sphinx.ext.intersphinx",/d' -i docs/conf.py || die + + distutils-r1_python_prepare_all +} + +python_compile_all() { + if use doc; then + emake -C docs html + fi +} + +python_test() { + # Tests have non-standard assumptions about PYTHONPATH, + # and don't work with ${BUILD_DIR}/lib. + PYTHONPATH=. "${PYTHON}" tests/runtests.py --settings=test_sqlite -v1 \ + || die "Tests fail with ${EPYTHON}" +} + +src_test() { + # Port conflict in django.test.testcases.LiveServerTestCase. + # Several other races with temp files. + DISTUTILS_NO_PARALLEL_BUILD=1 distutils-r1_src_test +} + +src_install() { + distutils-r1_src_install + webapp_src_install +} + +python_install_all() { + newbashcomp extras/django_bash_completion ${PN} + + if use doc; then + rm -fr docs/_build/html/_sources + local HTML_DOCS=( docs/_build/html/. ) + fi + + insinto "${MY_HTDOCSDIR#${EPREFIX}}" + doins -r django/contrib/admin/static/admin/. + distutils-r1_python_install_all +} + +pkg_postinst() { + elog "A copy of the admin media is available to webapp-config for installation in a" + elog "webroot, as well as the traditional location in python's site-packages dir" + elog "for easy development." + webapp_pkg_postinst +} diff --git a/dev-python/django/files/1.7-test_serialize.patch b/dev-python/django/files/1.7-test_serialize.patch new file mode 100644 index 000000000000..03509db74a07 --- /dev/null +++ b/dev-python/django/files/1.7-test_serialize.patch @@ -0,0 +1,507 @@ +https://github.com/django/django/commit/8c12d51ea27479555e226894c50c83043211d71d +diff --git a/django/conf/global_settings.py b/django/conf/global_settings.py +index a116da4..6d15063 100644 +--- a/django/conf/global_settings.py ++++ b/django/conf/global_settings.py +@@ -578,6 +578,10 @@ + # The name of the class to use to run the test suite + TEST_RUNNER = 'django.test.runner.DiscoverRunner' + ++# Apps that don't need to be serialized at test database creation time ++# (only apps with migrations are to start with) ++TEST_NON_SERIALIZED_APPS = [] ++ + ############ + # FIXTURES # + ############ +diff --git a/django/core/management/commands/flush.py b/django/core/management/commands/flush.py +index 38196ac..29e3a8e 100644 +--- a/django/core/management/commands/flush.py ++++ b/django/core/management/commands/flush.py +@@ -22,10 +22,9 @@ class Command(NoArgsCommand): + make_option('--no-initial-data', action='store_false', dest='load_initial_data', default=True, + help='Tells Django not to load any initial data after database synchronization.'), + ) +- help = ('Returns the database to the state it was in immediately after ' +- 'migrate was first executed. This means that all data will be removed ' +- 'from the database, any post-migration handlers will be ' +- 're-executed, and the initial_data fixture will be re-installed.') ++ help = ('Removes ALL DATA from the database, including data added during ' ++ 'migrations. Unmigrated apps will also have their initial_data ' ++ 'fixture reloaded. Does not achieve a "fresh install" state.') + + def handle_noargs(self, **options): + database = options.get('database') +@@ -54,7 +53,7 @@ def handle_noargs(self, **options): + if interactive: + confirm = input("""You have requested a flush of the database. + This will IRREVERSIBLY DESTROY all data currently in the %r database, +-and return each table to a fresh state. ++and return each table to an empty state. + Are you sure you want to do this? + + Type 'yes' to continue, or 'no' to cancel: """ % connection.settings_dict['NAME']) +diff --git a/django/core/management/commands/testserver.py b/django/core/management/commands/testserver.py +index 0409660..78885bb 100644 +--- a/django/core/management/commands/testserver.py ++++ b/django/core/management/commands/testserver.py +@@ -27,7 +27,7 @@ def handle(self, *fixture_labels, **options): + addrport = options.get('addrport') + + # Create a test database. +- db_name = connection.creation.create_test_db(verbosity=verbosity, autoclobber=not interactive) ++ db_name = connection.creation.create_test_db(verbosity=verbosity, autoclobber=not interactive, serialize=False) + + # Import the fixture data into the test database. + call_command('loaddata', *fixture_labels, **{'verbosity': verbosity}) +diff --git a/django/db/backends/creation.py b/django/db/backends/creation.py +index 13d4789..2934bee 100644 +--- a/django/db/backends/creation.py ++++ b/django/db/backends/creation.py +@@ -7,6 +7,11 @@ + from django.utils.encoding import force_bytes + from django.utils.functional import cached_property + from django.utils.six.moves import input ++from django.utils.six import StringIO ++from django.core.management.commands.dumpdata import sort_dependencies ++from django.db import router ++from django.apps import apps ++from django.core import serializers + + from .utils import truncate_name + +@@ -332,7 +337,7 @@ def sql_destroy_indexes_for_fields(self, model, fields, style): + ";", + ] + +- def create_test_db(self, verbosity=1, autoclobber=False, keepdb=False): ++ def create_test_db(self, verbosity=1, autoclobber=False, keepdb=False, serialize=True): + """ + Creates a test database, prompting the user for confirmation if the + database already exists. Returns the name of the test database created. +@@ -364,25 +369,31 @@ def create_test_db(self, verbosity=1, autoclobber=False, keepdb=False): + settings.DATABASES[self.connection.alias]["NAME"] = test_database_name + self.connection.settings_dict["NAME"] = test_database_name + +- # Report migrate messages at one level lower than that requested. ++ # We report migrate messages at one level lower than that requested. + # This ensures we don't get flooded with messages during testing +- # (unless you really ask to be flooded) +- call_command('migrate', ++ # (unless you really ask to be flooded). ++ call_command( ++ 'migrate', + verbosity=max(verbosity - 1, 0), + interactive=False, + database=self.connection.alias, +- load_initial_data=False, +- test_database=True) +- +- # We need to then do a flush to ensure that any data installed by +- # custom SQL has been removed. The only test data should come from +- # test fixtures, or autogenerated from post_migrate triggers. +- # This has the side effect of loading initial data (which was +- # intentionally skipped in the syncdb). +- call_command('flush', ++ test_database=True, ++ ) ++ ++ # We then serialize the current state of the database into a string ++ # and store it on the connection. This slightly horrific process is so people ++ # who are testing on databases without transactions or who are using ++ # a TransactionTestCase still get a clean database on every test run. ++ if serialize: ++ self.connection._test_serialized_contents = self.serialize_db_to_string() ++ ++ # Finally, we flush the database to clean ++ call_command( ++ 'flush', + verbosity=max(verbosity - 1, 0), + interactive=False, +- database=self.connection.alias) ++ database=self.connection.alias ++ ) + + call_command('createcachetable', database=self.connection.alias) + +@@ -391,6 +402,44 @@ def create_test_db(self, verbosity=1, autoclobber=False, keepdb=False): + + return test_database_name + ++ def serialize_db_to_string(self): ++ """ ++ Serializes all data in the database into a JSON string. ++ Designed only for test runner usage; will not handle large ++ amounts of data. ++ """ ++ # Build list of all apps to serialize ++ from django.db.migrations.loader import MigrationLoader ++ loader = MigrationLoader(self.connection) ++ app_list = [] ++ for app_config in apps.get_app_configs(): ++ if ( ++ app_config.models_module is not None and ++ app_config.label in loader.migrated_apps and ++ app_config.name not in settings.TEST_NON_SERIALIZED_APPS ++ ): ++ app_list.append((app_config, None)) ++ # Make a function to iteratively return every object ++ def get_objects(): ++ for model in sort_dependencies(app_list): ++ if not model._meta.proxy and router.allow_migrate(self.connection.alias, model): ++ queryset = model._default_manager.using(self.connection.alias).order_by(model._meta.pk.name) ++ for obj in queryset.iterator(): ++ yield obj ++ # Serialise to a string ++ out = StringIO() ++ serializers.serialize("json", get_objects(), indent=None, stream=out) ++ return out.getvalue() ++ ++ def deserialize_db_from_string(self, data): ++ """ ++ Reloads the database with data from a string generated by ++ the serialize_db_to_string method. ++ """ ++ data = StringIO(data) ++ for obj in serializers.deserialize("json", data, using=self.connection.alias): ++ obj.save() ++ + def _get_test_db_name(self): + """ + Internal implementation - returns the name of the test DB that will be +diff --git a/django/test/runner.py b/django/test/runner.py +index 226238a..f4d0995 100644 +--- a/django/test/runner.py ++++ b/django/test/runner.py +@@ -298,7 +298,11 @@ def setup_databases(verbosity, interactive, keepdb=False, **kwargs): + connection = connections[alias] + if test_db_name is None: + test_db_name = connection.creation.create_test_db( +- verbosity, autoclobber=not interactive, keepdb=keepdb) ++ verbosity, ++ autoclobber=not interactive, ++ keepdb=keepdb, ++ serialize=connection.settings_dict.get("TEST_SERIALIZE", True), ++ ) + destroy = True + else: + connection.settings_dict['NAME'] = test_db_name +diff --git a/django/test/testcases.py b/django/test/testcases.py +index 53ea93f..86d2b15 100644 +--- a/django/test/testcases.py ++++ b/django/test/testcases.py +@@ -753,6 +753,12 @@ class TransactionTestCase(SimpleTestCase): + # Subclasses can define fixtures which will be automatically installed. + fixtures = None + ++ # If transactions aren't available, Django will serialize the database ++ # contents into a fixture during setup and flush and reload them ++ # during teardown (as flush does not restore data from migrations). ++ # This can be slow; this flag allows enabling on a per-case basis. ++ serialized_rollback = False ++ + def _pre_setup(self): + """Performs any pre-test setup. This includes: + +@@ -808,6 +814,17 @@ def _fixture_setup(self): + if self.reset_sequences: + self._reset_sequences(db_name) + ++ # If we need to provide replica initial data from migrated apps, ++ # then do so. ++ if self.serialized_rollback and hasattr(connections[db_name], "_test_serialized_contents"): ++ if self.available_apps is not None: ++ apps.unset_available_apps() ++ connections[db_name].creation.deserialize_db_from_string( ++ connections[db_name]._test_serialized_contents ++ ) ++ if self.available_apps is not None: ++ apps.set_available_apps(self.available_apps) ++ + if self.fixtures: + # We have to use this slightly awkward syntax due to the fact + # that we're using *args and **kwargs together. +@@ -844,12 +861,14 @@ def _fixture_teardown(self): + # Allow TRUNCATE ... CASCADE and don't emit the post_migrate signal + # when flushing only a subset of the apps + for db_name in self._databases_names(include_mirrors=False): ++ # Flush the database + call_command('flush', verbosity=0, interactive=False, + database=db_name, skip_checks=True, + reset_sequences=False, + allow_cascade=self.available_apps is not None, + inhibit_post_migrate=self.available_apps is not None) + ++ + def assertQuerysetEqual(self, qs, values, transform=repr, ordered=True, msg=None): + items = six.moves.map(transform, qs) + if not ordered: +diff --git a/docs/ref/migration-operations.txt b/docs/ref/migration-operations.txt +index 40ef384..95c9a65 100644 +--- a/docs/ref/migration-operations.txt ++++ b/docs/ref/migration-operations.txt +@@ -199,8 +199,9 @@ model:: + # We get the model from the versioned app registry; + # if we directly import it, it'll be the wrong version + Country = apps.get_model("myapp", "Country") +- Country.objects.create(name="USA", code="us") +- Country.objects.create(name="France", code="fr") ++ db_alias = schema_editor.connection.alias ++ Country.objects.create(name="USA", code="us", using=db_alias) ++ Country.objects.create(name="France", code="fr", using=db_alias) + + class Migration(migrations.Migration): + +@@ -236,6 +237,14 @@ Oracle). This should be safe, but may cause a crash if you attempt to use + the ``schema_editor`` provided on these backends; in this case, please + set ``atomic=False``. + ++.. warning:: ++ ++ RunPython does not magically alter the connection of the models for you; ++ any model methods you call will go to the default database unless you ++ give them the current database alias (available from ++ ``schema_editor.connection.alias``, where ``schema_editor`` is the second ++ argument to your function). ++ + SeparateDatabaseAndState + ------------------------ + +diff --git a/docs/ref/settings.txt b/docs/ref/settings.txt +index 683d0f4..64f2d6e 100644 +--- a/docs/ref/settings.txt ++++ b/docs/ref/settings.txt +@@ -2078,6 +2078,24 @@ Default: ``'django.test.runner.DiscoverRunner'`` + The name of the class to use for starting the test suite. See + :ref:`other-testing-frameworks`. + ++.. setting:: TEST_NON_SERIALIZED_APPS ++ ++TEST_NON_SERIALIZED_APPS ++------------------------ ++ ++Default: ``[]`` ++ ++In order to restore the database state between tests for TransactionTestCases ++and database backends without transactions, Django will :ref:`serialize the ++contents of all apps with migrations <test-case-serialized-rollback>` when it ++starts the test run so it can then reload from that copy before tests that ++need it. ++ ++This slows down the startup time of the test runner; if you have apps that ++you know don't need this feature, you can add their full names in here (e.g. ++``django.contrib.contenttypes``) to exclude them from this serialization ++process. ++ + .. setting:: THOUSAND_SEPARATOR + + THOUSAND_SEPARATOR +diff --git a/docs/releases/1.7.txt b/docs/releases/1.7.txt +index e1bc3e5..cbef6b4 100644 +--- a/docs/releases/1.7.txt ++++ b/docs/releases/1.7.txt +@@ -63,6 +63,10 @@ but a few of the key features are: + * ``initial_data`` fixtures are no longer loaded for apps with migrations; if + you want to load initial data for an app, we suggest you do it in a migration. + ++* Test rollback behaviour is different for apps with migrations; in particular, ++ Django will no longer emulate rollbacks on non-transactional databases or ++ inside ``TransactionTestCase`` :ref:`unless specifically asked <test-case-serialized-rollback>`. ++ + App-loading refactor + ~~~~~~~~~~~~~~~~~~~~ + +diff --git a/docs/topics/testing/advanced.txt b/docs/topics/testing/advanced.txt +index 13041c1..7c81240 100644 +--- a/docs/topics/testing/advanced.txt ++++ b/docs/topics/testing/advanced.txt +@@ -485,7 +485,7 @@ django.db.connection.creation + The creation module of the database backend also provides some utilities that + can be useful during testing. + +-.. function:: create_test_db([verbosity=1, autoclobber=False, keepdb=False]) ++.. function:: create_test_db([verbosity=1, autoclobber=False, keepdb=False, serialize=True]) + + Creates a new test database and runs ``migrate`` against it. + +@@ -507,6 +507,12 @@ can be useful during testing. + a new database will be created, prompting the user to remove + the existing one, if present. + ++ ``serialize`` determines if Django serializes the database into an ++ in-memory JSON string before running tests (used to restore the database ++ state between tests if you don't have transactions). You can set this to ++ False to significantly speed up creation time if you know you don't need ++ data persistance outside of test fixtures. ++ + Returns the name of the test database that it created. + + ``create_test_db()`` has the side effect of modifying the value of +diff --git a/docs/topics/testing/overview.txt b/docs/topics/testing/overview.txt +index 2d9808f..026bbd8 100644 +--- a/docs/topics/testing/overview.txt ++++ b/docs/topics/testing/overview.txt +@@ -234,6 +234,33 @@ the Django test runner reorders tests in the following way: + database by a given :class:`~django.test.TransactionTestCase` test, they + must be updated to be able to run independently. + ++.. _test-case-serialized-rollback: ++ ++Rollback emulation ++------------------ ++ ++Any initial data loaded in migrations will only be available in ``TestCase`` ++tests and not in ``TransactionTestCase`` tests, and additionally only on ++backends where transactions are supported (the most important exception being ++MyISAM). ++ ++Django can re-load that data for you on a per-testcase basis by ++setting the ``serialized_rollback`` option to ``True`` in the body of the ++``TestCase`` or ``TransactionTestCase``, but note that this will slow down ++that test suite by approximately 3x. ++ ++Third-party apps or those developing against MyISAM will need to set this; ++in general, however, you should be developing your own projects against a ++transactional database and be using ``TestCase`` for most tests, and thus ++not need this setting. ++ ++The initial serialization is usually very quick, but if you wish to exclude ++some apps from this process (and speed up test runs slightly), you may add ++those apps to :setting:`TEST_NON_SERIALIZED_APPS`. ++ ++Apps without migrations are not affected; ``initial_data`` fixtures are ++reloaded as usual. ++ + Other test conditions + --------------------- + +@@ -249,6 +276,7 @@ used. This behavior `may change`_ in the future. + + .. _may change: https://code.djangoproject.com/ticket/11505 + ++ + Understanding the test output + ----------------------------- + +diff --git a/docs/topics/testing/tools.txt b/docs/topics/testing/tools.txt +index c41e35d..1d55b2e 100644 +--- a/docs/topics/testing/tools.txt ++++ b/docs/topics/testing/tools.txt +@@ -600,9 +600,17 @@ to test the effects of commit and rollback: + guarantees that the rollback at the end of the test restores the database to + its initial state. + +- When running on a database that does not support rollback (e.g. MySQL with the +- MyISAM storage engine), ``TestCase`` falls back to initializing the database +- by truncating tables and reloading initial data. ++.. warning:: ++ ++ ``TestCase`` running on a database that does not support rollback (e.g. MySQL with the ++ MyISAM storage engine), and all instances of ``TransactionTestCase``, will ++ roll back at the end of the test by deleting all data from the test database ++ and reloading initial data for apps without migrations. ++ ++ Apps with migrations :ref:`will not see their data reloaded <test-case-serialized-rollback>`; ++ if you need this functionality (for example, third-party apps should enable ++ this) you can set ``serialized_rollback = True`` inside the ++ ``TestCase`` body. + + .. warning:: + +diff --git a/tests/migration_test_data_persistence/__init__.py b/tests/migration_test_data_persistence/__init__.py +new file mode 100644 +index 0000000..e69de29 +diff --git a/tests/migration_test_data_persistence/migrations/0001_initial.py b/tests/migration_test_data_persistence/migrations/0001_initial.py +new file mode 100644 +index 0000000..0b13e8b +--- /dev/null ++++ b/tests/migration_test_data_persistence/migrations/0001_initial.py +@@ -0,0 +1,34 @@ ++# -*- coding: utf-8 -*- ++from __future__ import unicode_literals ++ ++from django.db import models, migrations ++ ++ ++def add_book(apps, schema_editor): ++ apps.get_model("migration_test_data_persistence", "Book").objects.using( ++ schema_editor.connection.alias, ++ ).create( ++ title="I Love Django", ++ ) ++ ++ ++class Migration(migrations.Migration): ++ ++ dependencies = [ ++ ] ++ ++ operations = [ ++ migrations.CreateModel( ++ name='Book', ++ fields=[ ++ ('id', models.AutoField(verbose_name='ID', primary_key=True, serialize=False, auto_created=True)), ++ ('title', models.CharField(max_length=100)), ++ ], ++ options={ ++ }, ++ bases=(models.Model,), ++ ), ++ migrations.RunPython( ++ add_book, ++ ), ++ ] +diff --git a/tests/migration_test_data_persistence/migrations/__init__.py b/tests/migration_test_data_persistence/migrations/__init__.py +new file mode 100644 +index 0000000..e69de29 +diff --git a/tests/migration_test_data_persistence/models.py b/tests/migration_test_data_persistence/models.py +new file mode 100644 +index 0000000..1b0b795 +--- /dev/null ++++ b/tests/migration_test_data_persistence/models.py +@@ -0,0 +1,5 @@ ++from django.db import models ++ ++ ++class Book(models.Model): ++ title = models.CharField(max_length=100) +diff --git a/tests/migration_test_data_persistence/tests.py b/tests/migration_test_data_persistence/tests.py +new file mode 100644 +index 0000000..1b89c17 +--- /dev/null ++++ b/tests/migration_test_data_persistence/tests.py +@@ -0,0 +1,33 @@ ++from django.test import TransactionTestCase ++from .models import Book ++ ++ ++class MigrationDataPersistenceTestCase(TransactionTestCase): ++ """ ++ Tests that data loaded in migrations is available if we set ++ serialized_rollback = True. ++ """ ++ ++ available_apps = ["migration_test_data_persistence"] ++ serialized_rollback = True ++ ++ def test_persistence(self): ++ self.assertEqual( ++ Book.objects.count(), ++ 1, ++ ) ++ ++ ++class MigrationDataNoPersistenceTestCase(TransactionTestCase): ++ """ ++ Tests the failure case ++ """ ++ ++ available_apps = ["migration_test_data_persistence"] ++ serialized_rollback = False ++ ++ def test_no_persistence(self): ++ self.assertEqual( ++ Book.objects.count(), ++ 0, ++ ) + |