From 71f26a76c3b0c78177aa3998e9fb8cb11a44a51a Mon Sep 17 00:00:00 2001 From: Untone Date: Mon, 30 Jun 2025 23:51:46 +0300 Subject: [PATCH] invites-fix4 --- CHANGELOG.md | 1 + resolvers/admin.py | 49 +++++++++++++++++++++++++++++++++++++++------ resolvers/reader.py | 16 +++++++++------ 3 files changed, 54 insertions(+), 12 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7a3fcbed..c330278c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ - Исправлена ошибка в функции `admin_get_invites` в файле `resolvers/admin.py` - добавлено значение по умолчанию для поля `slug` в объектах `Author`, чтобы избежать ошибки "Cannot return null for non-nullable field Author.slug" - Исправлена ошибка в функции `admin_get_invites` - заменен несуществующий атрибут `Shout.created_by_author` на правильное получение автора через поле `created_by` - Исправлена функция `admin_delete_invites_batch` - завершена реализация для корректной обработки пакетного удаления приглашений +- Исправлена ошибка в функции `get_shouts_with_links` в файле `resolvers/reader.py` - добавлено значение по умолчанию для поля `slug` у авторов публикаций в полях `authors` и `created_by`, чтобы избежать ошибки "Cannot return null for non-nullable field Author.slug" ### Улучшения админ-панели для приглашений diff --git a/resolvers/admin.py b/resolvers/admin.py index 35c71721..ac5b6560 100644 --- a/resolvers/admin.py +++ b/resolvers/admin.py @@ -519,7 +519,7 @@ async def admin_get_shouts( "id": getattr(author, "id", None), "email": getattr(author, "email", None), "name": getattr(author, "name", None), - "slug": getattr(author, "slug", None), + "slug": getattr(author, "slug", None) or f"user-{getattr(author, 'id', 'unknown')}", } for author in ( getattr(shout, "authors", []) @@ -803,14 +803,50 @@ async def admin_get_invites( # Добавляем информацию о создателе публикации, если она доступна if created_by_author: - invite_dict["shout"]["created_by"] = { + # Создаем новый словарь для shout + shout_dict = {} + + # Копируем основные поля + if isinstance(invite_dict["shout"], dict): + shout_info = invite_dict["shout"] + shout_dict["id"] = shout_info.get("id") + shout_dict["title"] = shout_info.get("title") + shout_dict["slug"] = shout_info.get("slug") + else: + # Если это не словарь, берем данные напрямую из объекта invite.shout + shout_dict["id"] = invite.shout.id + shout_dict["title"] = invite.shout.title + shout_dict["slug"] = invite.shout.slug + + # Добавляем информацию о создателе + shout_dict["created_by"] = { "id": created_by_author.id, "name": created_by_author.name or "Без имени", "email": created_by_author.email, "slug": created_by_author.slug or f"user-{created_by_author.id}", } + + invite_dict["shout"] = shout_dict else: - invite_dict["shout"]["created_by"] = None + # Создаем новый словарь для shout + shout_dict = {} + + # Копируем основные поля + if isinstance(invite_dict["shout"], dict): + shout_info = invite_dict["shout"] + shout_dict["id"] = shout_info.get("id") + shout_dict["title"] = shout_info.get("title") + shout_dict["slug"] = shout_info.get("slug") + else: + # Если это не словарь, берем данные напрямую из объекта invite.shout + shout_dict["id"] = invite.shout.id + shout_dict["title"] = invite.shout.title + shout_dict["slug"] = invite.shout.slug + + # Указываем, что created_by отсутствует + shout_dict["created_by"] = None + + invite_dict["shout"] = shout_dict result_invites.append(invite_dict) @@ -1057,11 +1093,12 @@ async def admin_delete_invites_batch( logger.info(f"Пакетное удаление приглашений: удалено {deleted_count} приглашений") # Формируем результат - result = {"success": True, "error": None} + success = deleted_count > 0 + error = None if errors: - result["error"] = f"Удалено {deleted_count} приглашений. Ошибки: {', '.join(errors)}" + error = f"Удалено {deleted_count} приглашений. Ошибки: {', '.join(errors)}" - return result + return {"success": success, "error": error} except Exception as e: logger.error(f"Ошибка при пакетном удалении приглашений: {e!s}") diff --git a/resolvers/reader.py b/resolvers/reader.py index 8c596fe3..6231bc61 100644 --- a/resolvers/reader.py +++ b/resolvers/reader.py @@ -227,7 +227,7 @@ def get_shouts_with_links(info: GraphQLResolveInfo, q: select, limit: int = 20, shout_dict["created_by"] = { "id": main_author_id, "name": a.name, - "slug": a.slug, + "slug": a.slug or f"user-{main_author_id}", "pic": a.pic, } @@ -240,7 +240,7 @@ def get_shouts_with_links(info: GraphQLResolveInfo, q: select, limit: int = 20, shout_dict["updated_by"] = { "id": updated_author.id, "name": updated_author.name, - "slug": updated_author.slug, + "slug": updated_author.slug or f"user-{updated_author.id}", "pic": updated_author.pic, } else: @@ -259,7 +259,7 @@ def get_shouts_with_links(info: GraphQLResolveInfo, q: select, limit: int = 20, shout_dict["deleted_by"] = { "id": deleted_author.id, "name": deleted_author.name, - "slug": deleted_author.slug, + "slug": deleted_author.slug or f"user-{deleted_author.id}", "pic": deleted_author.pic, } else: @@ -315,9 +315,13 @@ def get_shouts_with_links(info: GraphQLResolveInfo, q: select, limit: int = 20, # logger.debug(f"Final main_topic for shout#{shout_id}: {main_topic}") if has_field(info, "authors") and hasattr(row, "authors"): - shout_dict["authors"] = ( - orjson.loads(row.authors) if isinstance(row.authors, str) else row.authors - ) + authors_data = orjson.loads(row.authors) if isinstance(row.authors, str) else row.authors + # Проверяем и добавляем значение по умолчанию для slug, если оно пустое + if authors_data: + for author in authors_data: + if not author.get("slug"): + author["slug"] = f"user-{author.get('id', 'unknown')}" + shout_dict["authors"] = authors_data if has_field(info, "media") and shout.media: # Обработка поля media