mirror of
https://github.com/tanrax/org-social-relay
synced 2026-01-10 06:53:33 +01:00
135 lines
4.6 KiB
Python
135 lines
4.6 KiB
Python
from rest_framework.views import APIView
|
|
from rest_framework.response import Response
|
|
from rest_framework import status
|
|
from django.core.cache import cache
|
|
import logging
|
|
|
|
from app.feeds.models import Post, Profile
|
|
from app.feeds.utils import get_parent_chain
|
|
from app.reactions.utils import get_reactions_for_post
|
|
from app.replies.utils import get_direct_replies_for_post
|
|
from app.boosts.utils import get_boosts_for_post
|
|
|
|
logger = logging.getLogger(__name__)
|
|
|
|
|
|
class InteractionsView(APIView):
|
|
"""Get all interactions (reactions, replies, boosts) for a specific post"""
|
|
|
|
def get(self, request):
|
|
post_url = request.query_params.get("post")
|
|
|
|
if not post_url:
|
|
return Response(
|
|
{
|
|
"type": "Error",
|
|
"errors": ["'post' parameter is required"],
|
|
"data": None,
|
|
},
|
|
status=status.HTTP_400_BAD_REQUEST,
|
|
)
|
|
|
|
# Parse the post URL format: https://feed.com/social.org#post_id
|
|
try:
|
|
if "#" not in post_url:
|
|
raise ValueError("Invalid post URL format")
|
|
feed_url, post_id = post_url.split("#", 1)
|
|
except ValueError:
|
|
return Response(
|
|
{
|
|
"type": "Error",
|
|
"errors": ["Invalid post URL format. Expected: feed_url#post_id"],
|
|
"data": None,
|
|
},
|
|
status=status.HTTP_400_BAD_REQUEST,
|
|
)
|
|
|
|
cache_key = f"interactions_{feed_url}_{post_id}"
|
|
cached_response = cache.get(cache_key)
|
|
|
|
if cached_response is not None:
|
|
return Response(cached_response, status=status.HTTP_200_OK)
|
|
|
|
# Find the original post
|
|
try:
|
|
profile = Profile.objects.get(feed=feed_url)
|
|
original_post = Post.objects.get(profile=profile, post_id=post_id)
|
|
except (Profile.DoesNotExist, Post.DoesNotExist):
|
|
return Response(
|
|
{
|
|
"type": "Error",
|
|
"errors": ["Post not found"],
|
|
"data": None,
|
|
},
|
|
status=status.HTTP_404_NOT_FOUND,
|
|
)
|
|
|
|
original_post_url = f"{feed_url}#{post_id}"
|
|
|
|
# Get reactions using shared utility function
|
|
reactions_qs = get_reactions_for_post(original_post_url)
|
|
reactions_data = [
|
|
{
|
|
"post": f"{reaction.profile.feed}#{reaction.post_id}",
|
|
"emoji": reaction.mood,
|
|
}
|
|
for reaction in reactions_qs
|
|
]
|
|
|
|
# Get replies using shared utility function
|
|
replies_qs = get_direct_replies_for_post(original_post_url)
|
|
replies_data = [f"{reply.profile.feed}#{reply.post_id}" for reply in replies_qs]
|
|
|
|
# Get boosts using shared utility function
|
|
boosts_qs = get_boosts_for_post(original_post_url)
|
|
boosts_data = [f"{boost.profile.feed}#{boost.post_id}" for boost in boosts_qs]
|
|
|
|
# Get parent chain
|
|
parent_chain = get_parent_chain(original_post)
|
|
|
|
# URL encode the post_url for the self link
|
|
from urllib.parse import quote
|
|
|
|
encoded_post_url = quote(post_url, safe="")
|
|
encoded_feed_url = quote(feed_url, safe="")
|
|
|
|
response_data = {
|
|
"type": "Success",
|
|
"errors": [],
|
|
"data": {
|
|
"reactions": reactions_data,
|
|
"replies": replies_data,
|
|
"boosts": boosts_data,
|
|
},
|
|
"meta": {
|
|
"post": original_post_url,
|
|
"total_reactions": len(reactions_data),
|
|
"total_replies": len(replies_data),
|
|
"total_boosts": len(boosts_data),
|
|
"parentChain": parent_chain,
|
|
},
|
|
"_links": {
|
|
"self": {
|
|
"href": f"/interactions/?post={encoded_post_url}",
|
|
"method": "GET",
|
|
},
|
|
"reactions": {
|
|
"href": f"/reactions/?feed={encoded_feed_url}",
|
|
"method": "GET",
|
|
},
|
|
"replies": {
|
|
"href": f"/replies/?post={encoded_post_url}",
|
|
"method": "GET",
|
|
},
|
|
"boosts": {
|
|
"href": f"/boosts/?post={encoded_post_url}",
|
|
"method": "GET",
|
|
},
|
|
},
|
|
}
|
|
|
|
# Cache permanently (will be cleared by scan_feeds task)
|
|
cache.set(cache_key, response_data, None)
|
|
|
|
return Response(response_data, status=status.HTTP_200_OK)
|