Add public shareable link for galleries

This commit is contained in:
krek0 2026-04-20 22:29:17 +02:00
parent b76a350c28
commit a875c2707b
7 changed files with 126 additions and 14 deletions

View file

@ -3,6 +3,7 @@
# SPDX-License-Identifier: GPL-3.0-or-later
import os
import uuid
import zipfile
from io import BytesIO
from pathlib import Path
@ -14,9 +15,10 @@ from django.core.mail import mail_admins
from django.db import IntegrityError
from django.http import HttpResponse
from django.http import JsonResponse
from django.shortcuts import redirect
from django.urls import reverse_lazy
from django.shortcuts import get_object_or_404, redirect
from django.urls import reverse, reverse_lazy
from django.utils.text import slugify
from django.views import View
from django.views.generic.dates import ArchiveIndexView, YearArchiveView
from django.views.generic.detail import DetailView
from django.views.generic.edit import DeleteView, FormView
@ -87,34 +89,29 @@ class PhotoDeleteView(PermissionRequiredMixin, DeleteView):
return reverse_lazy("photologue:pl-gallery", args=[slug])
class PhotoReportView(LoginRequiredMixin, DetailView):
class PhotoReportView(DetailView):
model = Photo
template_name = "photologue/photo_confirm_report.html"
def post(self, request, *args, **kwargs):
"""
Make photo private on POST.
"""
# Mark photo as private
photo = self.get_object()
photo.is_public = False
photo.save()
# Get gallery
galleries = photo.galleries.all()
gallery_slug = galleries[0].slug if galleries else ""
if not gallery_slug:
if gallery_slug:
url = reverse_lazy("photologue:pl-gallery", args=[gallery_slug])
else:
url = reverse_lazy("photologue:pl-gallery-archive")
url = reverse_lazy("photologue:pl-gallery", args=[gallery_slug])
url = request.build_absolute_uri(url)
# Send mail to managers
reporter = request.user.username if request.user.is_authenticated else "anonymous"
mail_admins(
subject=f"Abuse report for photo id {photo.pk}",
message=f"{self.request.user.username} reported an abuse for `{photo.title}`: {url}#lg=1&slide={photo.pk}",
message=f"{reporter} reported an abuse for `{photo.title}`: {url}#lg=1&slide={photo.pk}",
)
# Redirect to gallery
return redirect(url)
@ -165,7 +162,9 @@ class GalleryDetailView(LoginRequiredMixin, DetailView):
if "owner" in self.kwargs:
context["photos"] = context["photos"].filter(owner__id=self.kwargs["owner"])
# Increment the photo view count
if self.object.public_token:
public_path = reverse("photologue:pl-gallery-public", args=[self.object.public_token])
context["public_url"] = self.request.build_absolute_uri(public_path)
context["photos"].update(view_count=F("view_count") + 1)
@ -207,6 +206,42 @@ class GalleryDownload(LoginRequiredMixin, DetailView):
# return response
class GalleryPublicView(DetailView):
model = Gallery
template_name = "photologue/gallery_detail.html"
def get_object(self):
return get_object_or_404(Gallery, public_token=self.kwargs["token"])
def get(self, request, *args, **kwargs):
request.guest_mode = True
return super().get(request, *args, **kwargs)
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
context["photos"] = self.object.photos.filter(is_public=True).select_related("owner")
context["owners"] = []
context["guest_mode"] = True
context["photos"].update(view_count=F("view_count") + 1)
return context
class GalleryTokenView(LoginRequiredMixin, View):
def post(self, request, slug):
if not request.user.is_staff:
from django.core.exceptions import PermissionDenied
raise PermissionDenied
gallery = get_object_or_404(Gallery, slug=slug)
action = request.POST.get("action")
if action == "generate":
gallery.public_token = uuid.uuid4()
gallery.save()
elif action == "revoke":
gallery.public_token = None
gallery.save()
return redirect(reverse("photologue:pl-gallery", args=[slug]))
class GalleryUpload(PermissionRequiredMixin, FormView):
"""
Form to upload new photos in a gallery