From 17b9cf0ffc2bc3986efe7ffe5aba13d233551570 Mon Sep 17 00:00:00 2001
From: olegphenomenon <oleg.hasjanov@eestiinternet.ee>
Date: Fri, 4 Nov 2022 13:43:30 +0200
Subject: [PATCH] send expire email for multiyear domains

---
 .../notify_multiyears_expiration_domain.rb    | 46 +++++++++++++++++++
 .../domains/force_delete/set_force_delete.rb  |  1 +
 test/models/domain/force_delete_test.rb       | 15 ++++++
 test/models/epp/response/result/code_test.rb  |  6 ++-
 4 files changed, 66 insertions(+), 2 deletions(-)
 create mode 100644 app/interactions/domains/force_delete/notify_multiyears_expiration_domain.rb

diff --git a/app/interactions/domains/force_delete/notify_multiyears_expiration_domain.rb b/app/interactions/domains/force_delete/notify_multiyears_expiration_domain.rb
new file mode 100644
index 0000000000..b35f79c02e
--- /dev/null
+++ b/app/interactions/domains/force_delete/notify_multiyears_expiration_domain.rb
@@ -0,0 +1,46 @@
+module Domains
+  module ForceDelete
+    class NotifyMultiyearsExpirationDomain < Base
+      SCHEDULED_DATA = 2.days
+
+      def execute
+        return unless multiyear_registrations?
+
+        recipients.each do |recipient|
+          DomainExpireEmailJob.set(wait_until: send_time).perform_later(domain.id, recipient)
+        end
+      end
+
+      def send_time
+        domain.force_delete_start + SCHEDULED_DATA
+      end
+
+      def multiyear_registrations?
+        domain_expire = domain.valid_to.to_i
+        current_time = Time.zone.now.to_i
+
+        (domain_expire - current_time) >= 1.year.to_i
+      end
+
+      def recipients
+        filter_invalid_emails(domain.expired_domain_contact_emails)
+      end
+
+      def filter_invalid_emails(emails)
+        emails.select do |email|
+          valid = Truemail.valid?(email)
+
+          unless valid
+            Rails.logger.info('Unable to send DomainExpireMailer#expired email for '\
+                        "domain #{domain.name} (##{domain.id}) to invalid recipient #{email}")
+          end
+
+          valid
+        end
+      end
+    end
+  end
+end
+
+
+
diff --git a/app/interactions/domains/force_delete/set_force_delete.rb b/app/interactions/domains/force_delete/set_force_delete.rb
index d5f3aa871f..f7cde0cc38 100644
--- a/app/interactions/domains/force_delete/set_force_delete.rb
+++ b/app/interactions/domains/force_delete/set_force_delete.rb
@@ -8,6 +8,7 @@ def execute
         compose(PostSetProcess, inputs.to_h)
         compose(NotifyRegistrar, inputs.to_h)
         compose(NotifyByEmail, inputs.to_h)
+        compose(NotifyMultiyearsExpirationDomain, inputs.to_h)
       end
     end
   end
diff --git a/test/models/domain/force_delete_test.rb b/test/models/domain/force_delete_test.rb
index c333b12df7..116ce5d35a 100644
--- a/test/models/domain/force_delete_test.rb
+++ b/test/models/domain/force_delete_test.rb
@@ -516,6 +516,21 @@ def test_lifts_force_delete_after_bounce_changes
     assert_not @domain.force_delete_scheduled?
   end
 
+  def test_notification_multiyear_expiration_domain
+    @domain.update(valid_to: Time.zone.parse('2014-08-05'))
+    assert_not @domain.force_delete_scheduled?
+    travel_to Time.zone.parse('2010-07-05')
+
+    @domain.schedule_force_delete(type: :soft)
+    @domain.reload
+
+    assert @domain.force_delete_scheduled?
+    assert_equal Date.parse('2010-09-19'), @domain.force_delete_date.to_date
+    assert_equal Date.parse('2010-08-05'), @domain.force_delete_start.to_date
+
+    assert_enqueued_jobs 4
+  end
+
   def prepare_bounced_email_address(email)
     @bounced_mail = BouncedMailAddress.new
     @bounced_mail.email = email
diff --git a/test/models/epp/response/result/code_test.rb b/test/models/epp/response/result/code_test.rb
index 8e424aa70c..76a62537b8 100644
--- a/test/models/epp/response/result/code_test.rb
+++ b/test/models/epp/response/result/code_test.rb
@@ -64,6 +64,8 @@ def test_returns_code_values
   end
 
   def test_returns_default_descriptions
+    ENV["shunter_default_threshold"] = '100'
+
     descriptions = {
       1000 => 'Command completed successfully',
       1001 => 'Command completed successfully; action pending',
@@ -92,8 +94,8 @@ def test_returns_default_descriptions
       2400 => 'Command failed',
       2501 => 'Authentication error; server closing connection'
     }
-
-    assert Epp::Response::Result::Code.default_descriptions.contain? descriptions
+    assert_equal descriptions, Epp::Response::Result::Code.default_descriptions
+    ENV["shunter_default_threshold"] = '10000'
   end
 
   def test_equality