diff --git a/backend/apps/owasp/graphql/nodes/snapshot.py b/backend/apps/owasp/graphql/nodes/snapshot.py index 53c15fd783..9f69adfce4 100644 --- a/backend/apps/owasp/graphql/nodes/snapshot.py +++ b/backend/apps/owasp/graphql/nodes/snapshot.py @@ -17,6 +17,7 @@ class SnapshotNode(GenericEntityNode): """Snapshot node.""" key = graphene.String() + summary = graphene.String() # ✅ Added to expose summary new_chapters = graphene.List(ChapterNode) new_issues = graphene.List(IssueNode) new_projects = graphene.List(ProjectNode) @@ -36,6 +37,10 @@ def resolve_key(self, info): """Resolve key.""" return self.key + def resolve_summary(self, info): + """Resolve generated summary of the snapshot.""" + return self.generate_summary() + def resolve_new_chapters(self, info): """Resolve new chapters.""" return self.new_chapters.all() diff --git a/backend/apps/owasp/models/snapshot.py b/backend/apps/owasp/models/snapshot.py index 6b4edf7acc..a1e5e2c0e3 100644 --- a/backend/apps/owasp/models/snapshot.py +++ b/backend/apps/owasp/models/snapshot.py @@ -51,3 +51,22 @@ def save(self, *args, **kwargs): self.key = now().strftime("%Y-%m") super().save(*args, **kwargs) + + def generate_summary(self): + """Generate a brief summary of the snapshot contents.""" + parts = [] + + if self.new_chapters.exists(): + parts.append(f"{self.new_chapters.count()} chapters") + if self.new_issues.exists(): + parts.append(f"{self.new_issues.count()} issues") + if self.new_projects.exists(): + parts.append(f"{self.new_projects.count()} projects") + if self.new_releases.exists(): + parts.append(f"{self.new_releases.count()} releases") + if self.new_users.exists(): + parts.append(f"{self.new_users.count()} users") + + if parts: + return "Added: " + ", ".join(parts) + return "No new entities added in this snapshot." diff --git a/frontend/src/components/SnapshotCard.tsx b/frontend/src/components/SnapshotCard.tsx index 78da8c999d..0a7dcc13cc 100644 --- a/frontend/src/components/SnapshotCard.tsx +++ b/frontend/src/components/SnapshotCard.tsx @@ -4,12 +4,19 @@ import { Button } from '@heroui/button' import { SnapshotCardProps } from 'types/card' import { formatDate } from 'utils/dateFormatter' -const SnapshotCard = ({ title, button, startAt, endAt }: SnapshotCardProps) => { +const SnapshotCard = ({ title, button, startAt, endAt, summary }: SnapshotCardProps) => { return (