I’m following up in regards to a question that I asked earlier in which I sought to seek a conversion from a goofy/poorly written mysql query to postgresql. I believe I succeeded with that. Anyways, I’m using data that was manually moved from a mysql database to a postgres database. I’m using a query that looks like so:
UPDATE krypdos_coderound cru
set is_correct = case
when t.kv_values1 = t.kv_values2 then True
else False
end
from
(select cr.id,
array_agg(
case when kv1.code_round_id = cr.id
then kv1.option_id
else null end
) as kv_values1,
array_agg(
case when kv2.code_round_id = cr_m.id
then kv2.option_id
else null end
) as kv_values2
from krypdos_coderound cr
join krypdos_value kv1 on kv1.code_round_id = cr.id
join krypdos_coderound cr_m
on cr_m.object_id=cr.object_id
and cr_m.content_type_id =cr.content_type_id
join krypdos_value kv2 on kv2.code_round_id = cr_m.id
WHERE
cr.is_master= False
AND cr_m.is_master= True
AND cr.object_id=%s
AND cr.content_type_id=%s
GROUP BY cr.id
) t
where t.id = cru.id
""" % ( self.object_id, self.content_type.id)
)
I have reason to believe that this works well. However, this has lead to a new issue. When trying to submit, I get an error from django that states:
IntegrityError at (some url):
duplicate key value violates unique constraint "krypdos_value_pkey"
I’ve looked at several of the responses posted on here and I haven’t quite found the solution to my problem (although the related questions have made for some interesting reading). I see this in my logs, which is interesting because I never explicitly call insert- django must handle it:
STATEMENT: INSERT INTO "krypdos_value" ("code_round_id", "variable_id", "option_id", "confidence", "freetext")
VALUES (1105935, 11, 55, NULL, E'')
RETURNING "krypdos_value"."id"
However, trying to run that results in the duplicate key error. The actual error is thrown in the code below.
# Delete current coding
CodeRound.objects.filter(
object_id=o.id, content_type=object_type, is_master=True
).delete()
code_round = CodeRound(
object_id=o.id,
content_type=object_type,
coded_by=request.user, comments=request.POST.get('_comments',None),
is_master=True,
)
code_round.save()
for key in request.POST.keys():
if key[0] != '_' or key != 'csrfmiddlewaretoken':
options = request.POST.getlist(key)
for option in options:
Value(
code_round=code_round,
variable_id=key,
option_id=option,
confidence=request.POST.get('_confidence_'+key, None),
).save() #This is where it dies
# Resave to set is_correct
code_round.save()
o.status = '3'
o.save()
I’ve checked the sequences and such and they seem to be in order. At this point I’m not sure what to do- I assume it’s something on django’s end but I’m not sure. Any feedback would be much appreciated!
Всем привет. Делаю сайт, конкретно форму добавления постов. При попытке сохранить пост появляется вот такая ошибка:
IntegrityError at /form ОШИБКА: повторяющееся значение ключа нарушает ограничение уникальности "sitelogic_post_post_slug_key" DETAIL: Ключ "(post_slug)=()" уже существует.
База данных — PostgreSQL
Пожалуйста, помогите разобраться в чем проблема. Искал ответ в большом количестве источников, нигде не нашел решения
Models.py:
class Post(models.Model):
post_title = models.CharField(max_length=250, verbose_name='Заголовок')
post_slug = models.SlugField(max_length=250, unique=True, verbose_name='URL')
post_content = models.TextField(max_length=450000, verbose_name='Содержание')
post_time_create = models.DateTimeField(auto_now_add=True, verbose_name='Время создания')
post_time_update = models.DateTimeField(auto_now=True, verbose_name='Время обновления')
post_media = models.ImageField(upload_to='%Y/%m/%d/', default='default.png', blank=True, verbose_name='Медиа')
cat = models.ForeignKey('PostCategory', on_delete=models.PROTECT, null=True, verbose_name='Категория')
def __str__(self):
return self.post_title
def get_absolute_url(self):
return reverse('show_post', kwargs={'post_title_slug': self.post_title, 'post_id_slug': self.id})
class Meta:
verbose_name = 'Пост'
verbose_name_plural = 'Посты'
ordering = ['post_title', 'post_content']
class PostCategory(models.Model):
category_name = models.CharField(max_length=100, db_index=True)
slug = models.SlugField(max_length=100, unique=True, verbose_name='URL')
class Meta:
verbose_name = 'Категория'
verbose_name_plural = 'Категории'
ordering = ['pk']
def __str__(self):
return self.category_name
def get_absolute_url(self):
return reverse('cat_posts', kwargs={'cat_slug': self.slug})
Forms.py:
class PostForm(forms.ModelForm):
captcha = CaptchaField()
class Meta:
model = Post
fields = ['post_title', 'post_content', 'post_media', 'cat']
def clean_post_title(self):
post_title = self.cleaned_data['post_title']
if len(post_title) >= 250:
raise ValidationError('Длина превышает 200 символов')
return post_title
Views.py:
class FormAdd(View):
def get(self, request):
form = PostForm
return render(request, 'sitelogic/addpost.html', context={'form': form})
def post(self, request):
request_keep = PostForm(request.POST)
if request_keep.is_valid():
request_keep.save()
return redirect('home_page')
return render(request, 'sitelogic/addpost.html', context={'form': request_keep})
Urls.py:
urlpatterns = [
path('', homepage, name='home_page'),
path('about', About.as_view(), name='about_site'),
path('post/<slug:post_title_slug>/<int:post_id_slug>/', ShowPost, name='show_post'),
path('forums/<slug:cat_slug>', ShowCategory.as_view(), name='cat_posts'),
path('form', FormAdd.as_view(), name='add_post'),
path('cabinet', Cabinet.as_view(), name='cabinet'),
path('auth/', include('djoser.urls')),
path('api/token/', TokenObtainPairView.as_view(), name='token_obtain_pair'),
path('api/token/refresh/', TokenRefreshView.as_view(), name='token_refresh'),
path('api/token/verify/', TokenVerifyView.as_view(), name='token_verify'),
path('testapi', Base.as_view())
] + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)
+ static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
Addpost.html:
{% extends 'sitelogic/base.html' %}
{% block body %}
<form action="{% url 'add_post' %}" method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<button type="submit">добавить</button>
</form>
{% endblock %}
Я слежу за вопросом который я задал ранее, в котором я пытался найти конверсию из тупого/плохо написанного запроса mysql в postgresql. Я считаю, что мне это удалось. В любом случае, я использую данные, которые были вручную перемещены из базы данных mysql в базу данных postgres. Я использую запрос, который выглядит так:
"""
UPDATE krypdos_coderound cru
set is_correct = case
when t.kv_values1 = t.kv_values2 then True
else False
end
from
(select cr.id,
array_agg(
case when kv1.code_round_id = cr.id
then kv1.option_id
else null end
) as kv_values1,
array_agg(
case when kv2.code_round_id = cr_m.id
then kv2.option_id
else null end
) as kv_values2
from krypdos_coderound cr
join krypdos_value kv1 on kv1.code_round_id = cr.id
join krypdos_coderound cr_m
on cr_m.object_id=cr.object_id
and cr_m.content_type_id =cr.content_type_id
join krypdos_value kv2 on kv2.code_round_id = cr_m.id
WHERE
cr.is_master= False
AND cr_m.is_master= True
AND cr.object_id=%s
AND cr.content_type_id=%s
GROUP BY cr.id
) t
where t.id = cru.id
""" % ( self.object_id, self.content_type.id)
)
У меня есть основания полагать, что это хорошо работает. Однако это привело к новой проблеме. При попытке отправить, я получаю сообщение об ошибке из django, в котором говорится:
IntegrityError at (some url):
duplicate key value violates unique constraint "krypdos_value_pkey"
Я просмотрел несколько ответов, размещенных здесь, и я не нашел решения моей проблемы (хотя связанные вопросы сделали для некоторого интересного чтения). Я вижу это в своих журналах, что интересно, потому что я никогда не называю insert-django явным образом:
STATEMENT: INSERT INTO "krypdos_value" ("code_round_id", "variable_id", "option_id", "confidence", "freetext")
VALUES (1105935, 11, 55, NULL, E'')
RETURNING "krypdos_value"."id"
Тем не менее, попытка выполнить это приводит к дублированию ключевой ошибки. Фактическая ошибка указана в коде ниже.
# Delete current coding CodeRound.objects.filter(object_id=o.id,content_type=object_type,is_master=True).delete()
code_round = CodeRound(object_id=o.id,content_type=object_type,coded_by=request.user,comments=request.POST.get('_comments',None),is_master=True)
code_round.save()
for key in request.POST.keys():
if key[0] != '_' or key != 'csrfmiddlewaretoken':
options = request.POST.getlist(key)
for option in options:
Value(code_round=code_round,variable_id=key,option_id=option,confidence=request.POST.get('_confidence_'+key, None)).save() #This is where it dies
# Resave to set is_correct
code_round.save()
o.status = '3'
o.save(
Я проверил последовательности и такие, и они, похоже, в порядке. На данный момент я не уверен, что делать — я предполагаю, что это что-то на django, но я не уверен. Любая обратная связь будет высоко оценена!
#django #postgresql #django-models #django-orm #unique-constraint
#django #postgresql #django-модели #django-orm #уникальное ограничение
Вопрос:
Я использую PostgreSQL с Django, и я пытался получить некоторый объект из БД с помощью Django ORM.
Medicine.objects.get(unique_item_id=26775)
Но во время выборки я столкнулся с ошибкой -> item_medicine.models.DoesNotExist: Medicine matching query does not exist.
Затем я попытался вставить то же самое, используя Django ORM.
Medicine.objects.create(unique_item_id=26775)
Но снова я получаю ошибку psycopg2.errors.UniqueViolation: duplicate key value violates unique constraint "item_medicine_medicine_unique_item_id_key" DETAIL: Key (unique_item_id)=(26775) already exists.
В моих моделях я добавил unique=True
unique_item_id
поле for .
Я не знаю, почему это происходит. Я пробовал ответы, приведенные на похожие сообщения, но ничего не сработало.
Трассировка:
Traceback (most recent call last):
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/backends/utils.py", line 64, in execute
return self.cursor.execute(sql, params)
psycopg2.errors.UniqueViolation: duplicate key value violates unique constraint "item_medicine_medicine_unique_item_id_key"
DETAIL: Key (unique_item_id)=(26775) already exists.
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/IPython/core/interactiveshell.py", line 2963, in run_code
exec(code_obj, self.user_global_ns, self.user_ns)
File "<ipython-input-4-46fdec6a582b>", line 1, in <module>
Medicine.objects.create(unique_item_id=26775)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/manager.py", line 85, in manager_method
return getattr(self.get_queryset(), name)(*args, **kwargs)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/query.py", line 394, in create
obj.save(force_insert=True, using=self.db)
File "/home/rohit/Projects/medicine/item_medicine/models.py", line 58, in save
super(Medicine, self).save(*args, **kwargs)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/base.py", line 808, in save
force_update=force_update, update_fields=update_fields)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/base.py", line 838, in save_base
updated = self._save_table(raw, cls, force_insert, force_update, using, update_fields)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/base.py", line 924, in _save_table
result = self._do_insert(cls._base_manager, using, fields, update_pk, raw)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/base.py", line 963, in _do_insert
using=using, raw=raw)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/manager.py", line 85, in manager_method
return getattr(self.get_queryset(), name)(*args, **kwargs)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/query.py", line 1076, in _insert
return query.get_compiler(using=using).execute_sql(return_id)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/models/sql/compiler.py", line 1112, in execute_sql
cursor.execute(sql, params)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/backends/utils.py", line 79, in execute
return super(CursorDebugWrapper, self).execute(sql, params)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/backends/utils.py", line 64, in execute
return self.cursor.execute(sql, params)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/utils.py", line 94, in __exit__
six.reraise(dj_exc_type, dj_exc_value, traceback)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/utils/six.py", line 685, in reraise
raise value.with_traceback(tb)
File "/home/rohit/virtualenvs/envmedicine/lib/python3.6/site-packages/django/db/backends/utils.py", line 64, in execute
return self.cursor.execute(sql, params)
django.db.utils.IntegrityError: duplicate key value violates unique constraint "item_medicine_medicine_unique_item_id_key"
DETAIL: Key (unique_item_id)=(26775) already exists.
Заранее спасибо, ребята!!
Комментарии:
1. Я не уверен, что вызвало проблему, но вы пробовали
Medicine.objects.filter(unique_item_id=26775).first()
?2. Я попробовал filter, но он возвращает пустой набор запросов
3. попробуйте это Medicine.objects.get(unique_item_id_id =26775)
4. Нет, поле ошибки получения не существует
5. Это немного странно, это происходит только с PostgreSQL? Если да, то можно ли его воспроизвести в новом проекте ? @RohitChopra
Ответ №1:
Если вы выполняете какую-либо фильтрацию в своем Medicine.objects
менеджере, вы, вероятно, столкнетесь с этой проблемой. Например, предположим, что у вас определены следующие модель и менеджер.
class SoftDeleteManager(models.Manager):
def get_queryset(self):
return super().get_queryset().filter(deleted_at=None)
class Medecine(models.Model):
...
unique_item_id = models.IntegerField(unique=True)
deleted_at = models.DateTimeField(null=True)
objects = SoftDeleteManager()
conflicting = Medecine.objects.create(unique_item_id=26775, deleted_at=some_datetime)
Medecine.objects.get(unique_item_id=26775) # Results in DoesNotExist
Medecine.objects.create(unique_item_id=26775) # Results in IntegrityError
Если это не так, то у вас может быть поврежден индекс PostgreSQL.
Я бы посоветовал вам попробовать запустить REINDEX
команду на вашем столе
REINDEX TABLE item_medicine_medicine
Комментарии:
1. Действительно, и я бы посоветовал проверить, что происходит непосредственно в БД, используя psql в консоли или pgAdmin. выберите * из лекарства, где unique_item_id = 26775.
2. «… любой вид фильтрации… тогда вы, вероятно, столкнетесь с этой проблемой …» Не могли бы вы объяснить, почему? В чем основная причина? Я знаю, что это есть в вашем примере, но краткое объяснение было бы очень полезно. 🙂
3. Ошибка фильтрации базового менеджера также упоминается в документах: don-t-filter-away-any-results-in-this-type-of-manager-subclass
При публикации страницы в django-cms (3.5.0) может возникнуть ошибка:
Exception Type: IntegrityError at /admin/cms/page/312/ru/publish/ Exception Value: ОШИБКА: повторяющееся значение ключа нарушает ограничение уникальности "spec_pageext_extended_object_id_key" DETAIL: Ключ "(extended_object_id)=(324)" уже существует.
По-английски:
django.db.utils.IntegrityError: duplicate key value violates unique constraint "spec_pageext_extended_object_id_key" DETAIL: Key (extended_object_id)=(324) already exists.
Из трейсбека понятно, что ошибка связана с Extension
(Расширение страницы).
Ещё нужно сказать, что ошибка не всегда проявляется при публикации страницы. Чтобы воспроизвести ошибку нужно:
- Создать расширение (или по-другому «Сохранить» из Меню / Страница / Моё расширение)
- Опубликовать страницу
- Перейти на черновую версию, щёлкнув «Изменить»
- Удалить расширение (Перейдя в Меню / Страница / Моё расширение и щёлкнув «Удалить»)
- Снова создать расширение (Меню / Страница / Моё расширение)
- И попытаться опубликовать страницу.
На шестом шаге появляется ошибка.
Оказывается при публикации не стирается старый объект Extension
и возникает исключение уникальности ключа. Поэтому я написал Mixin
, который перед выполнением операций по публикации Extension
удалаяет старое Extension
со страницы:
class ExtensionFixMixin(object): def copy_to_public(self, public_object, language): if not self.public_extension: try: self.__class__.objects.get(extended_object_id=public_object.pk).delete() except self.__class__.DoesNotExist: pass return super(ExtensionFixMixin, self).copy_to_public(public_object, language)
Теперь можно использовать в своих расширениях:
class MyExtension(ExtensionFixMixin, PageExtension): ...
Оказывается, есть тикет на гитхабе пакета django-cms , где встречается эта ошибка. Я дополнил тикет своим комментарием. Мое решение — это обходной путь. Как именно в самой django-cms поправить я сильно не смотрел. Надеюсь, разработчики поправят это дело.
Оцените статью
После нажатия кнопки «Отправить» ваше сообщение будет доставлено мне на почту.
Артём Мальцев
Веб-разработчик, владеющий знаниями языка программирования Python, фреймворка Django, системы управления содержимым сайта Django CMS, платформы для создания интернет-магазина Django Shop и многих различных приложений, использующих эти технологии.
Права на использование материала, расположенного на этой странице https://vivazzi.pro/ru/it/extended-object-id-already-exists/:
Разрешается копировать материал с указанием её автора и ссылки на оригинал без использования параметра rel="nofollow"
в теге <a>
. Использование:
Автор статьи: Артём Мальцев
Ссылка на статью: <a href="https://vivazzi.pro/ru/it/extended-object-id-already-exists/">https://vivazzi.pro/ru/it/extended-object-id-already-exists/</a>
Больше: Правила использования сайта
Представляю вашему вниманию книгу, написанную моим близким другом Максимом Макуриным: Секреты эффективного управления ассортиментом.
Книга предназначается для широкого круга читателей и, по мнению автора, будет полезна специалистам отдела закупок и логистики, категорийным и финансовым менеджерам, менеджерам по продажам, аналитикам, руководителям и директорам, в компетенции которых принятие решений по управлению ассортиментом.