From 504b7cfc95540e04e1febe42a72d2a8c032f4b6f Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:24:42 +0200 Subject: [PATCH 01/23] django.core.urlresolvers -> django.urls --- django_mongoengine/mongo_admin/options.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/django_mongoengine/mongo_admin/options.py b/django_mongoengine/mongo_admin/options.py index 2729461..618f88f 100644 --- a/django_mongoengine/mongo_admin/options.py +++ b/django_mongoengine/mongo_admin/options.py @@ -3,7 +3,7 @@ from django import forms from django.forms.formsets import all_valid -from django.core.urlresolvers import reverse +from django.urls import reverse from django.contrib.admin.exceptions import DisallowedModelAdminToField from django.contrib.admin import widgets, helpers from django.contrib.admin.utils import ( From 15f5f5ef855e9f7731ae159d36bcca8e2b7322f9 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:32:54 +0200 Subject: [PATCH 02/23] django.core.urlresolvers -> django.urls --- tests/views/edit.py | 2 +- tests/views/views.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/views/edit.py b/tests/views/edit.py index 99d5ae2..f8d184d 100644 --- a/tests/views/edit.py +++ b/tests/views/edit.py @@ -4,7 +4,7 @@ import unittest from django.core.exceptions import ImproperlyConfigured -from django.core.urlresolvers import reverse +from django.urls import reverse from django.views.generic.edit import FormMixin from django_mongoengine import forms diff --git a/tests/views/views.py b/tests/views/views.py index fc2cd1d..9dc9f52 100644 --- a/tests/views/views.py +++ b/tests/views/views.py @@ -4,7 +4,7 @@ from django.contrib.auth.decorators import login_required from django.core.paginator import Paginator -from django.core.urlresolvers import reverse +from django.urls import reverse from django.utils.decorators import method_decorator from django.views.generic import TemplateView From 126d7153f36df975e267db02cc70a850b43f640a Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:33:51 +0200 Subject: [PATCH 03/23] flake8 fixes --- django_mongoengine/document.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/django_mongoengine/document.py b/django_mongoengine/document.py index 4af4752..9ac8634 100644 --- a/django_mongoengine/document.py +++ b/django_mongoengine/document.py @@ -52,14 +52,17 @@ class Document(django_meta(mtc.TopLevelDocumentMetaclass, DjangoFlavor, me.Document)): swap_base = True + class DynamicDocument(django_meta(mtc.TopLevelDocumentMetaclass, DjangoFlavor, me.DynamicDocument)): swap_base = True + class EmbeddedDocument(django_meta(mtc.DocumentMetaclass, DjangoFlavor, me.EmbeddedDocument)): swap_base = True + class DynamicEmbeddedDocument(django_meta(mtc.DocumentMetaclass, - DjangoFlavor, me.DynamicEmbeddedDocument)): + DjangoFlavor, me.DynamicEmbeddedDocument)): swap_base = True From c3d330a568d2785aab97c1f8d5233f021ccd9cb7 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:37:26 +0200 Subject: [PATCH 04/23] drop django 1.8 support --- .travis.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index abc9157..1e7f007 100644 --- a/.travis.yml +++ b/.travis.yml @@ -6,7 +6,6 @@ python: - "3.5" - "pypy" env: - - DJANGO_VERSION=1.8.18 - DJANGO_VERSION=1.11.10 # command to install dependencies install: From d99a68bb74c4d3de95baef75d3f53374ff88ebcc Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:43:26 +0200 Subject: [PATCH 05/23] ModelState changed; support django 2.0 --- django_mongoengine/document.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/django_mongoengine/document.py b/django_mongoengine/document.py index 9ac8634..57ce77a 100644 --- a/django_mongoengine/document.py +++ b/django_mongoengine/document.py @@ -38,7 +38,8 @@ class DjangoFlavor(object): _get_pk_val = Model.__dict__["_get_pk_val"] def __init__(self, *args, **kwargs): - self._state = ModelState(self._meta.get("db_alias", me.DEFAULT_CONNECTION_NAME)) + self._state = ModelState() + self._state.db = self._meta.get("db_alias", me.DEFAULT_CONNECTION_NAME) super(DjangoFlavor, self).__init__(*args, **kwargs) def _get_unique_checks(self, exclude=None): From 09abe278939a2bca6802d8a5d0738e73541fd9dd Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 14:50:11 +0200 Subject: [PATCH 06/23] fixed tests redirects --- tests/views/edit.py | 46 ++++++++++++++++++++++----------------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/tests/views/edit.py b/tests/views/edit.py index f8d184d..6252b05 100644 --- a/tests/views/edit.py +++ b/tests/views/edit.py @@ -43,7 +43,7 @@ def test_create(self): 'name': 'Randall Munroe', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -63,7 +63,7 @@ def test_create_with_object_url(self): 'name': 'Rene Magritte'}) self.assertEqual(res.status_code, 302) artist = Artist.objects.get(name='Rene Magritte') - self.assertRedirects(res, 'http://testserver/detail/artist/%s/' % + self.assertRedirects(res, '/detail/artist/%s/' % artist.pk) self.assertQuerysetEqual(Artist.objects.all(), ['']) @@ -74,7 +74,7 @@ def test_create_with_redirect(self): 'name': 'Randall Munroe', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/edit/authors/create/') + self.assertRedirects(res, '/edit/authors/create/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -87,7 +87,7 @@ def test_create_with_interpolated_redirect(self): ['']) self.assertEqual(res.status_code, 302) pk = Author.objects.all()[0].pk - self.assertRedirects(res, 'http://testserver/edit/author/%s/update/' % + self.assertRedirects(res, '/edit/author/%s/update/' % pk) def test_create_with_special_properties(self): @@ -112,10 +112,10 @@ def test_create_with_special_properties(self): def test_create_without_redirect(self): try: - self.client.post('/edit/authors/create/naive/', - {'id': 1, - 'name': 'Randall Munroe', - 'slug': 'randall-munroe'}) + self.client.post('/edit/authors/create/naive/', { + 'id': 1, + 'name': 'Randall Munroe', + 'slug': 'randall-munroe'}) self.fail( 'Should raise exception -- No redirect URL provided, and no get_absolute_url provided') except ImproperlyConfigured: @@ -144,7 +144,7 @@ def test_update_post(self): 'name': 'Randall Munroe (xkcd)', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -165,7 +165,7 @@ def test_update_put(self): # the form will be invalid and redisplayed with errors (status code 200). # See also #12635 self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -189,7 +189,7 @@ def test_update_with_object_url(self): {'id': '1', 'name': 'Rene Magritte'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/detail/artist/%s/' % a.pk) + self.assertRedirects(res, '/detail/artist/%s/' % a.pk) self.assertQuerysetEqual(Artist.objects.all(), ['']) @@ -202,7 +202,7 @@ def test_update_with_redirect(self): 'name': 'Randall Munroe (author of xkcd)', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/edit/authors/create/') + self.assertRedirects(res, '/edit/authors/create/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -219,7 +219,7 @@ def test_update_with_interpolated_redirect(self): ['']) self.assertEqual(res.status_code, 302) pk = Author.objects.all()[0].pk - self.assertRedirects(res, 'http://testserver/edit/author/%s/update/' % + self.assertRedirects(res, '/edit/author/%s/update/' % pk) def test_update_with_special_properties(self): @@ -239,7 +239,7 @@ def test_update_with_special_properties(self): 'name': 'Randall Munroe (author of xkcd)', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/detail/author/%s/' % a.pk) + self.assertRedirects(res, '/detail/author/%s/' % a.pk) self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -248,10 +248,10 @@ def test_update_without_redirect(self): a = Author.objects.create(id='1', name='Randall Munroe', slug='randall-munroe', ) - self.client.post('/edit/author/%s/update/naive/' % a.pk, - {'id': '1', - 'name': 'Randall Munroe (author of xkcd)', - 'slug': 'randall-munroe'}) + self.client.post('/edit/author/%s/update/naive/' % a.pk, { + 'id': '1', + 'name': 'Randall Munroe (author of xkcd)', + 'slug': 'randall-munroe'}) self.fail( 'Should raise exception -- No redirect URL provided, and no get_absolute_url provided') except ImproperlyConfigured: @@ -274,7 +274,7 @@ def test_update_get_object(self): 'name': 'Randall Munroe (xkcd)', 'slug': 'randall-munroe'}) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), ['']) @@ -297,7 +297,7 @@ def test_delete_by_post(self): # Deletion with POST res = self.client.post('/edit/author/%s/delete/' % a.pk) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), []) def test_delete_by_delete(self): @@ -307,7 +307,7 @@ def test_delete_by_delete(self): 'slug': 'randall-munroe'}) res = self.client.delete('/edit/author/%s/delete/' % a.pk) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), []) def test_delete_with_redirect(self): @@ -316,7 +316,7 @@ def test_delete_with_redirect(self): 'slug': 'randall-munroe'}) res = self.client.post('/edit/author/%s/delete/redirect/' % a.pk) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/edit/authors/create/') + self.assertRedirects(res, '/edit/authors/create/') self.assertQuerysetEqual(Author.objects.all(), []) def test_delete_with_special_properties(self): @@ -332,7 +332,7 @@ def test_delete_with_special_properties(self): res = self.client.post('/edit/author/%s/delete/special/' % a.pk) self.assertEqual(res.status_code, 302) - self.assertRedirects(res, 'http://testserver/list/authors/') + self.assertRedirects(res, '/list/authors/') self.assertQuerysetEqual(Author.objects.all(), []) def test_delete_without_redirect(self): From 6873a3a07c6987a79904f5e94d08f3f741f39f3c Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:00:16 +0200 Subject: [PATCH 07/23] flake8 fixes --- django_mongoengine/views/edit.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/django_mongoengine/views/edit.py b/django_mongoengine/views/edit.py index 5b90868..1391b3e 100644 --- a/django_mongoengine/views/edit.py +++ b/django_mongoengine/views/edit.py @@ -20,6 +20,7 @@ # django 1.10 FormMixin = djmod.FormMixin + class WrapDocumentForm(WrapDocument, FormMixin): pass @@ -41,6 +42,7 @@ def get_success_url(self): " a get_absolute_url method on the Model.") return url + @copy_class(djmod.CreateView) class CreateView(six.with_metaclass( WrapDocumentForm, From a0ccd961ab616842341d1ba95e911288725965ba Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:00:23 +0200 Subject: [PATCH 08/23] tests update --- tests/views/edit.py | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/tests/views/edit.py b/tests/views/edit.py index 6252b05..8e4aa9a 100644 --- a/tests/views/edit.py +++ b/tests/views/edit.py @@ -244,7 +244,7 @@ def test_update_with_special_properties(self): ['']) def test_update_without_redirect(self): - try: + with self.assertRaises(ImproperlyConfigured): a = Author.objects.create(id='1', name='Randall Munroe', slug='randall-munroe', ) @@ -252,10 +252,6 @@ def test_update_without_redirect(self): 'id': '1', 'name': 'Randall Munroe (author of xkcd)', 'slug': 'randall-munroe'}) - self.fail( - 'Should raise exception -- No redirect URL provided, and no get_absolute_url provided') - except ImproperlyConfigured: - pass def test_update_get_object(self): a = Author.objects.create(pk='1', From 8ddef5d46952e400dfa3bfccb0e0f1e370348e4c Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:08:12 +0200 Subject: [PATCH 09/23] test matrix update; django 2.0 added --- .travis.yml | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 1e7f007..e9b3088 100644 --- a/.travis.yml +++ b/.travis.yml @@ -6,10 +6,17 @@ python: - "3.5" - "pypy" env: - - DJANGO_VERSION=1.11.10 + - DJANGO="Django>=1.11,<2.0" + - DJANGO="Django>=2.0,<2.2" +matrix: + exclude: + - python: "3.5" + env: DJANGO="Django>=1.11,<2.0" + - python: "pypy" + env: DJANGO="Django>=1.11,<2.0" # command to install dependencies install: - pip install -r requirements.txt - - pip install -q Django==$DJANGO_VERSION + - pip install -q $DJANGO # command to run tests script: python setup.py -q nosetests From 6f49091ce0a4cafc7401bf62056c1c7f18ecce37 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:10:20 +0200 Subject: [PATCH 10/23] travis config fix --- .travis.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index e9b3088..94efbf6 100644 --- a/.travis.yml +++ b/.travis.yml @@ -10,10 +10,10 @@ env: - DJANGO="Django>=2.0,<2.2" matrix: exclude: - - python: "3.5" - env: DJANGO="Django>=1.11,<2.0" + - python: "2.7" + env: DJANGO="Django>=2.0,<2.2" - python: "pypy" - env: DJANGO="Django>=1.11,<2.0" + env: DJANGO="Django>=2.0,<2.2" # command to install dependencies install: - pip install -r requirements.txt From af4f8ef696edc91691bb30c588bd77f27a41b3a9 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:14:39 +0200 Subject: [PATCH 11/23] readme/requirements update --- README.rst | 7 ++++--- requirements.txt | 2 +- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/README.rst b/README.rst index 549d1cd..63d2c30 100644 --- a/README.rst +++ b/README.rst @@ -8,10 +8,11 @@ Django-MongoEngine THIS IS UNSTABLE PROJECT, IF YOU WANT TO USE IT - FIX WHAT YOU NEED -Right now we're targeting to get things working on Django 1.9 +Right now we're targeting to get things working on Django 1.11 +2.0 support added, but not tested in production. -Working / Django 1.9 --------------------- +Working / Django 1.11 +--------------------- * [ok] sessions * [ok] models/fields, fields needs testing diff --git a/requirements.txt b/requirements.txt index 196caac..3dded73 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,2 +1,2 @@ -django>=1.7 +django>=1.11 mongoengine>=0.8.3 From 7633eb06761350f7882ac04e114d51b89ae8a76c Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 23 Feb 2018 15:26:16 +0200 Subject: [PATCH 12/23] version bump --- setup.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/setup.py b/setup.py index 33fe304..370c91f 100644 --- a/setup.py +++ b/setup.py @@ -12,10 +12,11 @@ """ from setuptools import setup, find_packages -import sys, os +import sys +import os -__version__ = '0.2.1' +__version__ = '0.3' __description__ = 'Django support for MongoDB via MongoEngine', __license__ = 'BSD' __author__ = 'Ross Lawley', From a11f9cfc16cab31d68847ff0709f59c51d6f239a Mon Sep 17 00:00:00 2001 From: g3ar Date: Sun, 4 Mar 2018 15:41:39 +0200 Subject: [PATCH 13/23] Media property added to DocumentAdmin Fixes `$ is not a function` error on document edit admin page. --- django_mongoengine/mongo_admin/options.py | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/django_mongoengine/mongo_admin/options.py b/django_mongoengine/mongo_admin/options.py index 5561fe2..732d5a3 100644 --- a/django_mongoengine/mongo_admin/options.py +++ b/django_mongoengine/mongo_admin/options.py @@ -263,6 +263,14 @@ def log_deletion(self, request, object, object_repr): return super(DocumentAdmin, self).log_deletion(request, object, object_repr) + def _media(self): + js = [ + 'vendor/jquery/jquery.min.js', + 'jquery.init.js', + ] + return forms.Media(js=['%s%s' % ('admin/js/', url) for url in js]) + media = property(_media) + @csrf_protect_m def changeform_view(self, request, object_id=None, form_url='', extra_context=None): From ac84d079dabb6669072ae3ad5b5f6abc98e63e94 Mon Sep 17 00:00:00 2001 From: g3ar Date: Sun, 4 Mar 2018 16:59:09 +0200 Subject: [PATCH 14/23] Media property in DocumentAdmin now using media from django ModelAdmin --- django_mongoengine/mongo_admin/options.py | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) diff --git a/django_mongoengine/mongo_admin/options.py b/django_mongoengine/mongo_admin/options.py index 732d5a3..ec263a9 100644 --- a/django_mongoengine/mongo_admin/options.py +++ b/django_mongoengine/mongo_admin/options.py @@ -263,13 +263,9 @@ def log_deletion(self, request, object, object_repr): return super(DocumentAdmin, self).log_deletion(request, object, object_repr) - def _media(self): - js = [ - 'vendor/jquery/jquery.min.js', - 'jquery.init.js', - ] - return forms.Media(js=['%s%s' % ('admin/js/', url) for url in js]) - media = property(_media) + @property + def media(self): + return djmod.ModelAdmin.media.fget(self) @csrf_protect_m def changeform_view(self, request, object_id=None, form_url='', extra_context=None): From 6875491fe174adc0a87901764ceaf82f3f25da09 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Mon, 19 Mar 2018 11:11:40 +0200 Subject: [PATCH 15/23] updated mongoengine version (issue #113) --- requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/requirements.txt b/requirements.txt index 3dded73..4133abd 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,2 +1,2 @@ django>=1.11 -mongoengine>=0.8.3 +mongoengine>=0.14 From 77e602949e12a6e11bc9f16e9f5efdd6bd44cec7 Mon Sep 17 00:00:00 2001 From: Erdenezul Batmunkh Date: Tue, 20 Mar 2018 14:41:53 +0800 Subject: [PATCH 16/23] required=True will give error about django-style blank --- docs/examples.rst | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/docs/examples.rst b/docs/examples.rst index 95bee4a..798d2f3 100644 --- a/docs/examples.rst +++ b/docs/examples.rst @@ -4,16 +4,25 @@ Examples Embedded Fields =============== - **models.py**:: - class ContactInfo(fields.EmbeddedDocument): + from django.db import models + from django_mongoengine import Document, EmbeddedDocument, fields + + class Product(Document): + name = fields.StringField() + retail_price = fields.DecimalField( + max_digits=15, decimal_places=2, default=0) + inventory_price = fields.DecimalField( + max_digits=15, decimal_places=2, default=0) + + class ContactInfo(EmbeddedDocument): web = fields.URLField(help_text=_("""List of languages for your application (the first one will be the default language)""")) email = fields.EmailField(verbose_name=_('e-mail address')) phone = fields.StringField(verbose_name=_('phone number')) class Application(Document): - name = fields.StringField(max_length=255, required=True) + name = fields.StringField(max_length=255, blank=False) contact = fields.EmbeddedDocumentField(ContactInfo) LOCALES = (('es', 'Spanish'), ('en', 'English'), ('de', 'German'), ('fr', 'French'), ('it', 'Italian'), ('ru', 'Russian')) locales = fields.ListField(fields.StringField(choices=LOCALES), help_text=_("""List of languages for your application (the first one will be the default language)""")) From 3a039964453ed03de03b7e63e93746ae4e589ca7 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Tue, 20 Mar 2018 12:12:24 +0200 Subject: [PATCH 17/23] readme update --- README.rst | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/README.rst b/README.rst index 63d2c30..63507a0 100644 --- a/README.rst +++ b/README.rst @@ -8,9 +8,15 @@ Django-MongoEngine THIS IS UNSTABLE PROJECT, IF YOU WANT TO USE IT - FIX WHAT YOU NEED -Right now we're targeting to get things working on Django 1.11 +Right now we're targeting to get things working on Django 1.11; 2.0 support added, but not tested in production. +WARNING: +-------- +Maybe there is better option for mongo support, take a look at https://nesdis.github.io/djongo/; +It's python3 only and i have not tried it yet, but looks promising. + + Working / Django 1.11 --------------------- From 690e1951a37e0d4894f48e48fc4f1293a9cb1a56 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E9=BB=8E=E4=B8=87=E6=88=90?= Date: Tue, 19 Jun 2018 16:50:58 +0800 Subject: [PATCH 18/23] Update __init__.py fix delete model bug: AttributeError: 'ObjectIdField' object has no attribute 'auto_created' --- django_mongoengine/fields/__init__.py | 3 +++ 1 file changed, 3 insertions(+) diff --git a/django_mongoengine/fields/__init__.py b/django_mongoengine/fields/__init__.py index a392df9..ae7ac2f 100644 --- a/django_mongoengine/fields/__init__.py +++ b/django_mongoengine/fields/__init__.py @@ -34,6 +34,9 @@ def patch_mongoengine_field(field_name): for k in ["__eq__", "__lt__", "__hash__", "attname"]: if k not in field.__dict__: setattr(field, k, djangoflavor.DjangoField.__dict__[k]) + # set auto_created False for check in django db model when delete + if field_name == "ObjectIdField": + setattr(field, "auto_created", False) for f in ["StringField", "ObjectIdField"]: From aa3e404bad5a31e18b0f4c975c55d05991034dc5 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Wed, 20 Jun 2018 15:08:32 +0300 Subject: [PATCH 19/23] imports update --- example/tumblelog/tumblelog/models.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/example/tumblelog/tumblelog/models.py b/example/tumblelog/tumblelog/models.py index 2143114..cefb356 100644 --- a/example/tumblelog/tumblelog/models.py +++ b/example/tumblelog/tumblelog/models.py @@ -1,4 +1,7 @@ -from django.core.urlresolvers import reverse +try: + from django.urls import reverse +except ImportError: + from django.core.urlresolvers import reverse from django_mongoengine import Document, EmbeddedDocument from django_mongoengine import fields @@ -14,6 +17,7 @@ class Comment(EmbeddedDocument): email = fields.EmailField(verbose_name="Email", blank=True) body = fields.StringField(verbose_name="Comment") + class Post(Document): created_at = fields.DateTimeField( default=datetime.datetime.now, editable=False, From 0aac4816cc6daf7258e23dbafb7cfe6127318680 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Wed, 20 Jun 2018 15:08:47 +0300 Subject: [PATCH 20/23] fix querysets (issue #119) --- django_mongoengine/mongo_auth/models.py | 25 +++++++++++++++++++++---- 1 file changed, 21 insertions(+), 4 deletions(-) diff --git a/django_mongoengine/mongo_auth/models.py b/django_mongoengine/mongo_auth/models.py index fee8a04..be4cfd2 100644 --- a/django_mongoengine/mongo_auth/models.py +++ b/django_mongoengine/mongo_auth/models.py @@ -15,8 +15,24 @@ from django_mongoengine import document from django_mongoengine import fields +from django_mongoengine.queryset import QuerySetManager from .managers import MongoUserManager + +def ct_init(self, *args, **kwargs): + super(QuerySetManager, self).__init__(*args, **kwargs) + self._cache = {} + + +ContentTypeManager = type( + "ContentTypeManager", + (QuerySetManager,), + dict( + ContentTypeManager.__dict__, + __init__=ct_init, + ), +) + try: from django.contrib.auth.hashers import check_password, make_password except ImportError: @@ -88,7 +104,7 @@ class SiteProfileNotAvailable(Exception): pass -class PermissionManager(models.Manager): +class PermissionManager(QuerySetManager): def get_by_natural_key(self, codename, app_label, model): return self.get( codename=codename, @@ -134,9 +150,10 @@ class Meta: def __unicode__(self): return u"%s | %s | %s" % ( - unicode(self.content_type.app_label), - unicode(self.content_type), - unicode(self.name)) + self.content_type.app_label, + self.content_type, + self.name, + ) def natural_key(self): return (self.codename,) + self.content_type.natural_key() From 57cd957a54b41e671634406d0a832e939704c381 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Wed, 20 Jun 2018 16:48:04 +0300 Subject: [PATCH 21/23] fix auto_created dupclication if set --- django_mongoengine/fields/djangoflavor.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/django_mongoengine/fields/djangoflavor.py b/django_mongoengine/fields/djangoflavor.py index 26b6532..5046e9c 100644 --- a/django_mongoengine/fields/djangoflavor.py +++ b/django_mongoengine/fields/djangoflavor.py @@ -28,6 +28,8 @@ def __init__(self, *args, **kwargs): if "required" in kwargs: raise ImproperlyConfigured("`required` option is not supported. Use Django-style `blank` instead.") kwargs["required"] = not kwargs["blank"] + if hasattr(self, "auto_created"): + kwargs.pop("auto_created") self.verbose_name = kwargs.pop("verbose_name", None) super(DjangoField, self).__init__(*args, **kwargs) self.remote_field = None From 7e548aa6f6c1a63c073cc3a49533b2f70f3f6d76 Mon Sep 17 00:00:00 2001 From: farhan-cashify Date: Tue, 3 Jul 2018 18:43:43 +0530 Subject: [PATCH 22/23] compatible with django 1.11 and admin working --- django_mongoengine/mongo_admin/options.py | 45 +++++------------------ django_mongoengine/mongo_admin/views.py | 29 +++++++++++++-- 2 files changed, 35 insertions(+), 39 deletions(-) diff --git a/django_mongoengine/mongo_admin/options.py b/django_mongoengine/mongo_admin/options.py index ec263a9..2a2a959 100644 --- a/django_mongoengine/mongo_admin/options.py +++ b/django_mongoengine/mongo_admin/options.py @@ -54,7 +54,7 @@ def get_content_type_for_model(obj): get_content_type_for_model=get_content_type_for_model, ) -class BaseDocumentAdmin(djmod.BaseModelAdmin): +class BaseDocumentAdmin(djmod.ModelAdmin): """Functionality common to both ModelAdmin and InlineAdmin.""" form = DocumentForm @@ -62,7 +62,6 @@ def formfield_for_dbfield(self, db_field, **kwargs): """ Hook for specifying the form Field instance for a given database Field instance. - If kwargs are given, they're passed to the form Field's constructor. """ request = kwargs.pop("request", None) @@ -162,10 +161,11 @@ def __init__(self, model, admin_site): self.model = model self.opts = model._meta self.admin_site = admin_site - super(DocumentAdmin, self).__init__() + super(DocumentAdmin, self).__init__(model, admin_site) self.log = not settings.DATABASES.get('default', {}).get( 'ENGINE', 'django.db.backends.dummy' ).endswith('dummy') + self.change_list_template = 'admin/change_document_list.html' # XXX: add inline init somewhere def _get_inline_instances(self): @@ -231,11 +231,17 @@ def get_changelist_formset(self, request, **kwargs): fields=self.list_editable, **defaults ) + def get_changelist(self, request, **kwargs): + """ + Returns the ChangeList class for use on the changelist page. + """ + from django_mongoengine.mongo_admin.views import DocumentChangeList + return DocumentChangeList + def log_addition(self, request, object, message): """ Log that an object has been successfully added. - The default implementation creates an admin LogEntry object. """ if not self.log: @@ -245,7 +251,6 @@ def log_addition(self, request, object, message): def log_change(self, request, object, message): """ Log that an object has been successfully changed. - The default implementation creates an admin LogEntry object. """ if not self.log: @@ -256,7 +261,6 @@ def log_deletion(self, request, object, object_repr): """ Log that an object will be deleted. Note that this method is called before the deletion. - The default implementation creates an admin LogEntry object. """ if not self.log: @@ -475,39 +479,10 @@ def history_view(self, request, object_id, extra_context=None): "admin/object_history.html" ], context) - def get_search_results(self, request, queryset, search_term): - """ - Returns a tuple containing a queryset to implement the search, - and a boolean indicating if the results may contain duplicates. - """ - # Apply keyword searches. - def construct_search(field_name): - if field_name.startswith('^'): - return "%s__istartswith" % field_name[1:] - elif field_name.startswith('='): - return "%s__iexact" % field_name[1:] - elif field_name.startswith('@'): - return "%s__search" % field_name[1:] - else: - return "%s__icontains" % field_name - - use_distinct = False - search_fields = self.get_search_fields(request) - if search_fields and search_term: - orm_lookups = [construct_search(str(search_field)) - for search_field in search_fields] - for bit in search_term.split(): - or_queries = [Q(**{orm_lookup: bit}) - for orm_lookup in orm_lookups] - queryset = queryset.filter(reduce(operator.or_, or_queries)) - - return queryset, use_distinct - class InlineDocumentAdmin(BaseDocumentAdmin): """ Options for inline editing of ``model`` instances. - Provide ``name`` to specify the attribute name of the ``ForeignKey`` from ``model`` to its parent. This is required if ``model`` has more than one ``ForeignKey`` to its parent. diff --git a/django_mongoengine/mongo_admin/views.py b/django_mongoengine/mongo_admin/views.py index 9dc0014..d1f1c92 100644 --- a/django_mongoengine/mongo_admin/views.py +++ b/django_mongoengine/mongo_admin/views.py @@ -9,6 +9,7 @@ from django.utils.encoding import smart_str from mongoengine import Q +from functools import reduce class DocumentChangeList(ChangeList): @@ -20,6 +21,7 @@ def __init__(self, request, model, list_display, list_display_links, request, model, list_display, list_display_links, list_filter, date_hierarchy, search_fields, list_select_related, list_per_page, list_max_show_all, list_editable, model_admin) + except TypeError: self.list_max_show_all = list_max_show_all # The init for django <= 1.3 takes one parameter less @@ -30,6 +32,17 @@ def __init__(self, request, model, list_display, list_display_links, self.pk_attname = self.lookup_opts.pk_name def get_results(self, request): + # query_set has been changed to queryset + try: + self.query_set + except: + self.query_set = self.queryset + # root_query_set has been changed to root_queryset + try: + self.root_query_set + except: + self.root_query_set = self.root_queryset + paginator = self.model_admin.get_paginator(request, self.query_set, self.list_per_page) # Get the number of objects, with admin filters applied. @@ -106,9 +119,12 @@ def get_ordering(self, request=None, queryset=None): continue # Invalid ordering specified, skip it. # Add the given query's ordering fields, if any. - sign = lambda t: t[1] > 0 and '+' or '-' - qs_ordering = [sign(t) + t[0] for t in queryset._ordering] - ordering.extend(qs_ordering) + try: + sign = lambda t: t[1] > 0 and '+' or '-' + qs_ordering = [sign(t) + t[0] for t in queryset._ordering] + ordering.extend(qs_ordering) + except: + pass # Ensure that the primary key is systematically present in the list of # ordering fields so we can guarantee a deterministic order across all @@ -152,7 +168,12 @@ def _lookup_param_1_3(self): ) return lookup_params - def get_query_set(self, request=None): + def get_queryset(self, request=None): + # root_query_set has been changed to root_queryset + try: + self.root_query_set + except: + self.root_query_set = self.root_queryset # First, we collect all the declared list filters. qs = self.root_query_set.clone() From b03d7586a0ac456982d1563acf231041c2a39e20 Mon Sep 17 00:00:00 2001 From: Sergey Tereschenko Date: Fri, 13 Jul 2018 12:11:14 +0300 Subject: [PATCH 23/23] admin fixes --- django_mongoengine/mongo_admin/views.py | 26 ++++++------------------- 1 file changed, 6 insertions(+), 20 deletions(-) diff --git a/django_mongoengine/mongo_admin/views.py b/django_mongoengine/mongo_admin/views.py index d1f1c92..73594df 100644 --- a/django_mongoengine/mongo_admin/views.py +++ b/django_mongoengine/mongo_admin/views.py @@ -13,22 +13,8 @@ class DocumentChangeList(ChangeList): - def __init__(self, request, model, list_display, list_display_links, - list_filter, date_hierarchy, search_fields, list_select_related, - list_per_page, list_max_show_all, list_editable, model_admin): - try: - super(DocumentChangeList, self).__init__( - request, model, list_display, list_display_links, list_filter, - date_hierarchy, search_fields, list_select_related, - list_per_page, list_max_show_all, list_editable, model_admin) - - except TypeError: - self.list_max_show_all = list_max_show_all - # The init for django <= 1.3 takes one parameter less - super(DocumentChangeList, self).__init__( - request, model, list_display, list_display_links, list_filter, - date_hierarchy, search_fields, list_select_related, - list_per_page, list_editable, model_admin) + def __init__(self, *args, **kwargs): + super(DocumentChangeList, self).__init__(*args, **kwargs) self.pk_attname = self.lookup_opts.pk_name def get_results(self, request): @@ -42,7 +28,7 @@ def get_results(self, request): self.root_query_set except: self.root_query_set = self.root_queryset - + paginator = self.model_admin.get_paginator(request, self.query_set, self.list_per_page) # Get the number of objects, with admin filters applied. @@ -97,7 +83,7 @@ def get_ordering(self, request=None, queryset=None): ordering field. """ if queryset is None: - # with Django < 1.4 get_ordering works without fixes for mongoengine + # with Django < 1.4 get_ordering works without fixes for mongoengine return super(DocumentChangeList, self).get_ordering() params = self.params @@ -195,7 +181,7 @@ def get_queryset(self, request=None): # string (i.e. those that haven't already been processed by the # filters). qs = qs.filter(**remaining_lookup_params) - # TODO: This should probably be mongoengine exceptions + # TODO: This should probably be mongoengine exceptions except (SuspiciousOperation, ImproperlyConfigured): # Allow certain types of errors to be re-raised as-is so that the # caller can treat them in a special way. @@ -205,7 +191,7 @@ def get_queryset(self, request=None): # have any other way of validating lookup parameters. They might be # invalid if the keyword arguments are incorrect, or if the values # are not in the correct type, so we might get FieldError, - # ValueError, ValidationError, or ?. + # ValueError, ValidationError, or ?. raise IncorrectLookupParameters(e) # Set ordering.