diff --git a/app/services/discover/register.rb b/app/services/discover/register.rb new file mode 100644 index 000000000..297912413 --- /dev/null +++ b/app/services/discover/register.rb @@ -0,0 +1,37 @@ +module Discover + class Register + FOREM_DISCOVER_URL = "https://discover.forem.com/api/forems/register".freeze + + class RegisterError < StandardError; end + + def self.call(**args) + new(**args).call + end + + def initialize(domain: Settings::General.app_domain) + @domain = domain + end + + def call + return unless @domain + return if Rails.env.development? + + response = HTTParty.post(FOREM_DISCOVER_URL, body: { domain: @domain }) + + unless response.success? + error_message = %( + "Discover::Register Error - Forem Discover registration error. + #{response.message}. + #{response.body}." + ) + Rails.logger.error(error_message) + + # raising an error to trigger the Sidekiq Worker to retry + raise RegisterError, "Discover::Register Error" + end + + Rails.logger.info(JSON.parse(response.parsed_response)["message"]) + true + end + end +end diff --git a/app/workers/discover/register_worker.rb b/app/workers/discover/register_worker.rb new file mode 100644 index 000000000..ce0db6f6e --- /dev/null +++ b/app/workers/discover/register_worker.rb @@ -0,0 +1,11 @@ +module Discover + class RegisterWorker + include Sidekiq::Worker + + sidekiq_options queue: :low_priority, retry: 3 + + def perform(domain = Settings::General.app_domain) + Discover::Register.call(domain: domain) + end + end +end diff --git a/spec/services/discover/register_spec.rb b/spec/services/discover/register_spec.rb new file mode 100644 index 000000000..9719ce3b2 --- /dev/null +++ b/spec/services/discover/register_spec.rb @@ -0,0 +1,60 @@ +require "rails_helper" + +RSpec.describe Discover::Register, type: :service do + let(:domain) { "https://discover.forem.com" } + + before { stub_const "#{described_class}::FOREM_DISCOVER_URL", domain } + + it "defines FOREM_DISCOVER_URL" do + expect(described_class.const_defined?(:FOREM_DISCOVER_URL)).to be true + end + + context "when the API call is successful" do + before { stub_successful_request } + + it "logs info with the parsed response message" do + allow(Rails.logger).to receive(:info).with("Forem registered successfully for #{domain}.") + described_class.call(domain: domain) + expect(Rails.logger).to have_received(:info).with("Forem registered successfully for #{domain}.") + end + + it "returns true" do + result = described_class.call(domain: domain) + expect(result).to eq true + end + end + + context "when there is an error with the API call" do + before { stub_unsuccessful_request } + + it "raises and logs an error" do + allow(Rails.logger).to receive(:error) + + expect do + described_class.call(domain: domain) + end.to raise_error(Discover::Register::RegisterError, "Discover::Register Error") + + expect(Rails.logger).to have_received(:error) + end + end + + def stub_successful_request + stub_request(:post, domain) + .to_return( + status: 200, + body: { + message: "Forem registered successfully for #{domain}." + }.to_json, + ) + end + + def stub_unsuccessful_request(error = "error") + stub_request(:post, domain) + .to_return( + status: 422, + body: { + errors: error + }.to_json, + ) + end +end diff --git a/spec/workers/discover/register_worker_spec.rb b/spec/workers/discover/register_worker_spec.rb new file mode 100644 index 000000000..931caa265 --- /dev/null +++ b/spec/workers/discover/register_worker_spec.rb @@ -0,0 +1,15 @@ +require "rails_helper" + +RSpec.describe Discover::RegisterWorker, type: :woker do + include_examples "#enqueues_on_correct_queue", "low_priority" + + describe "#perform" do + let(:worker) { subject } + + it "registers the Forem with the app_domain" do + allow(Discover::Register).to receive(:call) + worker.perform + expect(Discover::Register).to have_received(:call) + end + end +end