AI Update: شروع به پیاده سازی کن

This commit is contained in:
Antigravity Bot
2026-08-30 11:54:50 +03:30
parent c2a3cdc085
commit a5342b0850
4 changed files with 648 additions and 23 deletions
+197 -7
View File
@@ -1,11 +1,17 @@
import json
import asyncpg
from datetime import datetime, timezone
from typing import List, Optional, Dict, Any, Tuple
from db.models import SourceChannel, SourceWebsite, TargetChannel, Post, Setting, AILog, AIProviderProfile, ChannelCategory
from db.models import (
SourceChannel, SourceWebsite, TargetChannel, Post, Setting,
AILog, AIProviderProfile, ChannelCategory, AdminReviewChannel
)
from db.database import get_db_pool
def _parse_admin_channel_row(row: asyncpg.Record) -> AdminReviewChannel:
return AdminReviewChannel(**dict(row))
def _parse_post_row(row: asyncpg.Record) -> Post:
data = dict(row)
if isinstance(data.get("published_to"), str):
@@ -566,13 +572,19 @@ class Repository:
)
return [_parse_post_row(r) for r in rows]
async def update_review_message_id(self, post_id: int, review_message_id: int) -> None:
async def update_review_message_id(self, post_id: int, review_message_id: Optional[int], review_channel_id: Optional[int] = None) -> None:
pool = await self._get_pool()
async with pool.acquire() as conn:
await conn.execute(
"UPDATE posts SET review_message_id = $1 WHERE id = $2;",
review_message_id, post_id,
)
if review_channel_id is not None:
await conn.execute(
"UPDATE posts SET review_message_id = $1, review_channel_id = $2 WHERE id = $3;",
review_message_id, review_channel_id, post_id,
)
else:
await conn.execute(
"UPDATE posts SET review_message_id = $1 WHERE id = $2;",
review_message_id, post_id,
)
async def _upsert_published_entry(
self,
@@ -1044,6 +1056,184 @@ class Repository:
description="Global emergency operational pause"
)
# --- Admin Review Channels ---
async def add_admin_channel(
self,
channel_id: int,
title: Optional[str] = None,
username: Optional[str] = None,
is_default: bool = False
) -> int:
pool = await self._get_pool()
async with pool.acquire() as conn:
async with conn.transaction():
if is_default:
await conn.execute("UPDATE admin_channels SET is_default = FALSE;")
row = await conn.fetchrow(
"""
INSERT INTO admin_channels (channel_id, title, username, is_default, is_active)
VALUES ($1, $2, $3, $4, TRUE)
ON CONFLICT(channel_id) DO UPDATE SET
title = COALESCE(EXCLUDED.title, admin_channels.title),
username = COALESCE(EXCLUDED.username, admin_channels.username),
is_default = EXCLUDED.is_default,
is_active = TRUE
RETURNING id;
""",
channel_id, title, username, is_default
)
return row["id"]
async def get_admin_channels(self) -> List[AdminReviewChannel]:
pool = await self._get_pool()
async with pool.acquire() as conn:
rows = await conn.fetch("SELECT * FROM admin_channels WHERE is_active = TRUE ORDER BY is_default DESC, id ASC;")
return [_parse_admin_channel_row(r) for r in rows]
async def get_admin_channel_by_id(self, admin_id: int) -> Optional[AdminReviewChannel]:
pool = await self._get_pool()
async with pool.acquire() as conn:
row = await conn.fetchrow("SELECT * FROM admin_channels WHERE id = $1;", admin_id)
return _parse_admin_channel_row(row) if row else None
async def get_admin_channel_by_telegram_id(self, channel_id: int) -> Optional[AdminReviewChannel]:
pool = await self._get_pool()
async with pool.acquire() as conn:
row = await conn.fetchrow("SELECT * FROM admin_channels WHERE channel_id = $1;", channel_id)
return _parse_admin_channel_row(row) if row else None
async def get_default_admin_channel(self) -> Optional[AdminReviewChannel]:
pool = await self._get_pool()
async with pool.acquire() as conn:
row = await conn.fetchrow("SELECT * FROM admin_channels WHERE is_active = TRUE AND is_default = TRUE LIMIT 1;")
if not row:
row = await conn.fetchrow("SELECT * FROM admin_channels WHERE is_active = TRUE ORDER BY id ASC LIMIT 1;")
return _parse_admin_channel_row(row) if row else None
async def set_default_admin_channel(self, admin_id: int) -> None:
pool = await self._get_pool()
async with pool.acquire() as conn:
async with conn.transaction():
await conn.execute("UPDATE admin_channels SET is_default = FALSE;")
await conn.execute("UPDATE admin_channels SET is_default = TRUE WHERE id = $1;", admin_id)
async def delete_admin_channel(self, admin_id: int) -> None:
pool = await self._get_pool()
async with pool.acquire() as conn:
row = await conn.fetchrow("SELECT channel_id FROM admin_channels WHERE id = $1;", admin_id)
if row:
ch_id = row["channel_id"]
await conn.execute("UPDATE sources SET admin_channel_id = NULL WHERE admin_channel_id = $1;", ch_id)
await conn.execute("UPDATE source_websites SET admin_channel_id = NULL WHERE admin_channel_id = $1;", ch_id)
await conn.execute("DELETE FROM admin_channels WHERE id = $1;", admin_id)
# --- Source & Website Admin Channel Setters ---
async def set_source_admin_channel(self, source_id: int, admin_channel_id: Optional[int]) -> None:
pool = await self._get_pool()
async with pool.acquire() as conn:
await conn.execute("UPDATE sources SET admin_channel_id = $1 WHERE id = $2;", admin_channel_id, source_id)
async def set_website_admin_channel(self, site_id: int, admin_channel_id: Optional[int]) -> None:
pool = await self._get_pool()
async with pool.acquire() as conn:
await conn.execute("UPDATE source_websites SET admin_channel_id = $1 WHERE id = $2;", admin_channel_id, site_id)
# --- Review Purge Helpers ---
async def get_review_posts_by_admin_channel(self, admin_channel_id: int) -> List[Post]:
pool = await self._get_pool()
async with pool.acquire() as conn:
rows = await conn.fetch(
"""
SELECT * FROM posts
WHERE review_channel_id = $1
AND review_message_id IS NOT NULL
AND is_deleted = FALSE
ORDER BY id ASC;
""",
admin_channel_id
)
return [_parse_post_row(r) for r in rows]
async def count_review_posts_by_admin_channel(self, admin_channel_id: int) -> int:
pool = await self._get_pool()
async with pool.acquire() as conn:
val = await conn.fetchval(
"""
SELECT COUNT(*) FROM posts
WHERE review_channel_id = $1
AND review_message_id IS NOT NULL
AND is_deleted = FALSE;
""",
admin_channel_id
)
return val or 0
async def clear_review_messages_for_channel(self, admin_channel_id: int) -> List[Post]:
pool = await self._get_pool()
async with pool.acquire() as conn:
async with conn.transaction():
rows = await conn.fetch(
"""
SELECT * FROM posts
WHERE review_channel_id = $1
AND review_message_id IS NOT NULL
AND is_deleted = FALSE;
""",
admin_channel_id
)
posts = [_parse_post_row(r) for r in rows]
await conn.execute(
"""
UPDATE posts
SET review_message_id = NULL,
is_deleted = TRUE,
status = 'deleted'
WHERE review_channel_id = $1
AND review_message_id IS NOT NULL
AND is_deleted = FALSE;
""",
admin_channel_id
)
return posts
async def get_all_review_posts_with_message_id(self) -> List[Post]:
pool = await self._get_pool()
async with pool.acquire() as conn:
rows = await conn.fetch(
"""
SELECT * FROM posts
WHERE review_message_id IS NOT NULL
AND is_deleted = FALSE
ORDER BY id ASC;
"""
)
return [_parse_post_row(r) for r in rows]
async def clear_all_review_messages(self) -> List[Post]:
pool = await self._get_pool()
async with pool.acquire() as conn:
async with conn.transaction():
rows = await conn.fetch(
"""
SELECT * FROM posts
WHERE review_message_id IS NOT NULL
AND is_deleted = FALSE;
"""
)
posts = [_parse_post_row(r) for r in rows]
await conn.execute(
"""
UPDATE posts
SET review_message_id = NULL,
is_deleted = TRUE,
status = 'deleted'
WHERE review_message_id IS NOT NULL
AND is_deleted = FALSE;
"""
)
return posts