From 6c46bb575bfa1120d85aa54f67fad7531939616b Mon Sep 17 00:00:00 2001 From: Kabiru Mwenja Date: Thu, 2 Apr 2026 17:46:25 +0300 Subject: [PATCH] fix(reminders): check remindable access before creating notification (#22651) Ensure the scheduled reminder job verifies the creator still has access to the remindable before creating a notification, consistent with the visibility checks applied elsewhere. --- .../reminders/schedule_reminder_job.rb | 5 ++++ .../reminders/schedule_reminder_job_spec.rb | 24 ++++++++++++++++++- 2 files changed, 28 insertions(+), 1 deletion(-) diff --git a/app/workers/reminders/schedule_reminder_job.rb b/app/workers/reminders/schedule_reminder_job.rb index b8300d3c9bd..794eb7961c2 100644 --- a/app/workers/reminders/schedule_reminder_job.rb +++ b/app/workers/reminders/schedule_reminder_job.rb @@ -39,6 +39,11 @@ module Reminders def perform(reminder) return if reminder.unread_notifications? + unless reminder.visible?(reminder.creator) + reminder.update_column(:completed_at, Time.current) + return + end + create_notification_service = create_notification_from_reminder(reminder) create_notification_service.on_success do |service_result| diff --git a/spec/workers/reminders/schedule_reminder_job_spec.rb b/spec/workers/reminders/schedule_reminder_job_spec.rb index 44fb702a244..b479732b3ca 100644 --- a/spec/workers/reminders/schedule_reminder_job_spec.rb +++ b/spec/workers/reminders/schedule_reminder_job_spec.rb @@ -45,7 +45,11 @@ RSpec.describe Reminders::ScheduleReminderJob do end describe "#perform" do - let(:reminder) { create(:reminder) } + let(:role) { create(:project_role, permissions: %i[view_work_packages]) } + let(:project) { create(:project) } + let(:user) { create(:user, member_with_roles: { project => role }) } + let(:work_package) { create(:work_package, project:) } + let(:reminder) { create(:reminder, creator: user, remindable: work_package) } subject { described_class.new.perform(reminder) } @@ -66,6 +70,24 @@ RSpec.describe Reminders::ScheduleReminderJob do end end + context "when the creator no longer has access to the remindable" do + before { Member.where(principal: user, project:).destroy_all } + + it "does not create a notification" do + expect { subject }.not_to change(Notification, :count) + end + + it "does not enqueue a NotificationDeliveryJob" do + expect { subject } + .not_to have_enqueued_job(Mails::Reminders::NotificationDeliveryJob) + end + + it "marks the reminder as completed" do + subject + expect(reminder.reload).to be_completed + end + end + context "when the reminder is already notified" do before do create(:reminder_notification, reminder: reminder, notification: create(:notification, read_ian: false))