Skip to content

Commit

Permalink
moved english controlelrs methods to concern
Browse files Browse the repository at this point in the history
  • Loading branch information
OlegPhenomenon committed Jun 20, 2024
1 parent a37d91a commit e02dd8b
Show file tree
Hide file tree
Showing 5 changed files with 131 additions and 123 deletions.
85 changes: 85 additions & 0 deletions app/controllers/concerns/english_offers/offerable.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
module EnglishOffers
module Offerable
extend ActiveSupport::Concern

included do
before_render :find_or_initialize_autobidder, only: %i[new create edit update]
before_action :prevent_check_for_invalid_bid, only: [:update]
end

protected

def broadcast_update_auction_offer(auction)
Offers::UpdateBroadcastService.call({ auction: })
end

def update_auction_values(auction, message_text)
AutobiderService.autobid(auction)
auction.update_ends_at(@offer)

flash[:notice] = message_text
redirect_to root_path
end

def inform_about_invalid_bid_amount
formatted_starting_price = format('%.2f', @auction.starting_price)
flash[:alert] = t('english_offers.create.bid_must_be', minimum: formatted_starting_price)

if turbo_frame_request?
render turbo_stream: turbo_stream.action(:redirect, root_path)
else
redirect_to root_path, status: :see_other
end
end

def find_or_initialize_autobidder
@autobider = current_user&.autobiders&.find_or_initialize_by(domain_name: @auction.domain_name)
end

def prevent_check_for_invalid_bid
auction = Auction.with_user_offers(current_user.id).find_by(uuid: @offer.auction.uuid)

return unless bid_is_bad?(auction:, update_params:)

flash[:alert] =
"#{t('english_offers.show.bid_failed', price: format('%.2f', auction.highest_price.to_f).tr('.', ','))}"

if turbo_frame_request?
render turbo_stream: turbo_stream.action(:redirect, root_path)
else
redirect_to root_path, status: :see_other
end
end

def check_first_bid_for_english_auction(params, auction)
return true if auction.blind?

starting_price = auction.starting_price
price = params[:price].to_f

price.to_f >= starting_price.to_f
end

private

def bid_is_bad?(auction:, update_params:)
!additional_check_for_bids(auction, update_params[:price]) ||
!check_bids_for_english_auction(update_params, auction)
end

def additional_check_for_bids(auction, current_bid)
order = auction.offers.order(updated_at: :desc).first

Money.new(order.cents).to_f < current_bid.to_f
end

def check_bids_for_english_auction(params, auction)
return true if auction.blind?

minimum = auction.min_bids_step.to_f
price = params[:price].to_f

price >= minimum
end
end
end
14 changes: 11 additions & 3 deletions app/controllers/concerns/offerable.rb
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,17 @@ module Offerable
protected

def check_for_ban
if Ban.valid.where(user_id: current_user).where(domain_name: @auction.domain_name).any? || current_user.completely_banned?
redirect_to root_path, flash: { alert: I18n.t("#{params[:controller]}.create.ban") } and return
end
is_ban = Ban.valid.where(user_id: current_user).where(domain_name: @auction.domain_name).any?
is_ban ||= current_user.completely_banned?
return unless is_ban

redirect_to root_path, flash: { alert: I18n.t("#{params[:controller]}.create.ban") } and return
end

def inform_invalid_captcha
@show_checkbox_recaptcha = true unless @success
flash[:alert] = t('offers.form.captcha_verification')
redirect_to root_path, status: :see_other
end

private
Expand Down
135 changes: 28 additions & 107 deletions app/controllers/english_offers_controller.rb
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
# rubocop:disable Metrics
# frozen_string_literal: true

class EnglishOffersController < ApplicationController
include BeforeRender
include Offerable
protect_from_forgery with: :null_session

# order is important
before_action :set_offer, only: %i[show edit update]
before_render :find_or_initialize_autobidder, only: %i[new create edit update]
before_action :prevent_check_for_invalid_bid, only: [:update]
include EnglishOffers::Offerable

include RecaptchaValidatable
recaptcha_action 'english_offer'
Expand All @@ -22,40 +23,25 @@ def new

# POST /auctions/aa450f1a-45e2-4f22-b2c3-f5f46b5f906b/offers
def create
unless check_first_bid_for_english_auction(create_params, @auction)
formatted_starting_price = format('%.2f', @auction.starting_price)
flash[:alert] = t('english_offers.create.bid_must_be', minimum: formatted_starting_price)

if turbo_frame_request?
render turbo_stream: turbo_stream.action(:redirect, root_path)
else
redirect_to root_path, status: :see_other and return
end
end
inform_about_invalid_bid_amount and return unless check_first_bid_for_english_auction(create_params, @auction)
inform_invalid_captcha and return unless recaptcha_valid

@offer = Offer.new(create_params)
@offer.username = Username::GenerateUsernameService.new.call
authorize! :manage, @offer

if recaptcha_valid
if create_predicate(@auction)
broadcast_update_auction_offer(@auction)
send_outbided_notification(auction: @auction, offer: @offer, flash:)
update_auction_values(@auction, t('english_offers.create.created'))
else
flash[:alert] = if @offer.errors.full_messages_for(:cents).present?
@offer.errors.full_messages_for(:cents).join
else
@offer.errors.full_messages.join('; ')
end

redirect_to root_path and return
end
if create_predicate(@auction)
broadcast_update_auction_offer(@auction)
send_outbided_notification(auction: @auction, offer: @offer, flash:)
update_auction_values(@auction, t('english_offers.create.created'))
else
@show_checkbox_recaptcha = true unless @success
flash.now[:alert] = t('english_offers.form.captcha_verification')
flash[:alert] = if @offer.errors.full_messages_for(:cents).present?
@offer.errors.full_messages_for(:cents).join
else
@offer.errors.full_messages.join('; ')
end

redirect_to root_path, status: :see_other and return
redirect_to root_path and return
end
end

Expand All @@ -74,71 +60,24 @@ def edit
def update
@auction = Auction.english.with_user_offers(current_user.id).find_by(uuid: @offer.auction.uuid)
redirect_to auction_path(@auction.uuid) and return if update_not_allowed(@auction)
inform_invalid_captcha and return unless recaptcha_valid

if recaptcha_valid
if update_predicate(@auction)
broadcast_update_auction_offer(@auction)
send_outbided_notification(auction: @auction, offer: @offer, flash:)
update_auction_values(@auction, t('english_offers.edit.bid_updated'))
else
flash[:alert] = if @offer.errors.full_messages_for(:cents).present?
@offer.errors.full_messages_for(:cents).join
else
@offer.errors.full_messages.join('; ')
end

redirect_to root_path
end
if update_predicate(@auction)
broadcast_update_auction_offer(@auction)
send_outbided_notification(auction: @auction, offer: @offer, flash:)
update_auction_values(@auction, t('english_offers.edit.bid_updated'))
else
@show_checkbox_recaptcha = true unless @success
flash.now[:alert] = t('english_offers.form.captcha_verification')
redirect_to root_path, status: :see_other
end
end

private

def find_or_initialize_autobidder
@autobider = current_user&.autobiders&.find_or_initialize_by(domain_name: @auction.domain_name)
end

def broadcast_update_auction_offer(auction)
Offers::UpdateBroadcastService.call({ auction: })
end

def update_auction_values(auction, message_text)
AutobiderService.autobid(auction)
auction.update_ends_at(@offer)

flash[:notice] = message_text
redirect_to root_path
end

def prevent_check_for_invalid_bid
auction = Auction.with_user_offers(current_user.id).find_by(uuid: @offer.auction.uuid)

return unless bid_is_bad?(auction:, update_params:)
flash[:alert] = if @offer.errors.full_messages_for(:cents).present?
@offer.errors.full_messages_for(:cents).join
else
@offer.errors.full_messages.join('; ')
end

flash[:alert] =
"#{t('english_offers.show.bid_failed', price: format('%.2f', auction.highest_price.to_f).tr('.', ','))}"

if turbo_frame_request?
render turbo_stream: turbo_stream.action(:redirect, root_path)
else
redirect_to root_path, status: :see_other
redirect_to root_path
end
end

def bid_is_bad?(auction:, update_params:)
!additional_check_for_bids(auction, update_params[:price]) ||
!check_bids_for_english_auction(update_params, auction)
end

def additional_check_for_bids(auction, current_bid)
order = auction.offers.order(updated_at: :desc).first

Money.new(order.cents).to_f < current_bid.to_f
end
private

def create_predicate(auction)
@offer.save && auction.update_minimum_bid_step(create_params[:price].to_f) && @offer.reload
Expand All @@ -148,24 +87,6 @@ def create_params
params.require(:offer).permit(:auction_id, :user_id, :price, :billing_profile_id, :username)
end

def check_first_bid_for_english_auction(params, auction)
return true if auction.blind?

starting_price = auction.starting_price
price = params[:price].to_f

price.to_f >= starting_price.to_f
end

def check_bids_for_english_auction(params, auction)
return true if auction.blind?

minimum = auction.min_bids_step.to_f
price = params[:price].to_f

price >= minimum
end

def update_predicate(auction)
@offer.update(update_params) &&
auction.update_minimum_bid_step(create_params[:price].to_f) &&
Expand Down
16 changes: 6 additions & 10 deletions app/controllers/offers_controller.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
# frozen_string_literal: true

# rubocop:disable Metrics
class OffersController < ApplicationController
include Offerable

Expand All @@ -12,19 +11,18 @@ class OffersController < ApplicationController

# GET /auctions/aa450f1a-45e2-4f22-b2c3-f5f46b5f906b/offers/new
def new
prevent_check_for_existed_offer and return if @auction.offer_from_user(current_user.id)

BillingProfile.create_default_for_user(current_user.id)
@offer = Offer.new(auction_id: @auction.id, user_id: current_user.id)
end

# POST /auctions/aa450f1a-45e2-4f22-b2c3-f5f46b5f906b/offers
def create
existing_offer = @auction.offer_from_user(current_user.id)

@offer = Offer.new(create_params)
authorize! :manage, @offer

inform_invalid_captcha and return unless recaptcha_valid

respond_to do |format|
if existing_offer
format.html do
Expand All @@ -34,9 +32,7 @@ def create
format.html { redirect_to root_path, notice: t('.created') }
format.json { render :show, status: :created, location: @offer }
else
@show_checkbox_recaptcha = true unless @success
flash[:alert] = recaptcha_valid ? @offer.errors.full_messages.join('; ') : t('offers.form.captcha_verification')

flash[:alert] = @offer.errors.full_messages.join('; ')
format.html { redirect_to root_path, status: :see_other }
format.json { render json: @offer.errors, status: :unprocessable_entity }
end
Expand All @@ -63,16 +59,16 @@ def edit
# PUT /offers/aa450f1a-45e2-4f22-b2c3-f5f46b5f906b
def update
auction = @offer.auction

inform_invalid_captcha and return unless recaptcha_valid
redirect_to root_path and return if update_not_allowed(auction)

respond_to do |format|
if update_predicate
format.html { redirect_to root_path, notice: t(:updated), status: :see_other }
format.json { render :show, status: :ok, location: @offer }
else
@show_checkbox_recaptcha = true unless @success
flash[:alert] = recaptcha_valid ? @offer.errors.full_messages.join('; ') : t('offers.form.captcha_verification')

flash[:alert] = @offer.errors.full_messages.join('; ')
format.html { redirect_to root_path, status: :see_other }
format.json { render json: @offer.errors, status: :unprocessable_entity }
end
Expand Down
4 changes: 1 addition & 3 deletions test/integration/english_offers_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -152,9 +152,7 @@ def test_banned_user_cannot_create_an_offer
}
}

post auction_english_offers_path(auction_uuid: @auction.uuid),
params: params,
headers: { "HTTP_REFERER" => root_path }
post auction_english_offers_path(auction_uuid: @auction.uuid), params: params

assert_equal flash[:alert], I18n.t('english_offers.create.ban')
assert @auction.offers.empty?
Expand Down

0 comments on commit e02dd8b

Please sign in to comment.