mirror of
https://github.com/internetee/registry.git
synced 2025-07-01 08:43:37 +02:00
parent
3741e2d2a3
commit
58ae53b1e6
17 changed files with 264 additions and 13 deletions
|
@ -2,13 +2,25 @@ module Admin
|
|||
module Billing
|
||||
class PricesController < AdminController
|
||||
authorize_resource(class: 'Billing::Price')
|
||||
before_action :load_price, only: %i[edit update destroy]
|
||||
before_action :load_price, only: %i[edit update expire]
|
||||
helper_method :zones
|
||||
helper_method :operation_categories
|
||||
helper_method :durations
|
||||
|
||||
def index
|
||||
@q = ::Billing::Price.search(params[:q])
|
||||
@search = OpenStruct.new(search_params)
|
||||
|
||||
unless @search.validity
|
||||
@search.validity = 'unexpired'
|
||||
end
|
||||
|
||||
prices = ::Billing::Price.all
|
||||
|
||||
if @search.validity.present?
|
||||
prices = ::Billing::Price.send(@search.validity)
|
||||
end
|
||||
|
||||
@q = prices.search(params[:q])
|
||||
@q.sorts = ['zone_id asc', 'duration asc', 'operation_category asc',
|
||||
'valid_from desc', 'valid_to asc'] if @q.sorts.empty?
|
||||
@prices = @q.result.page(params[:page])
|
||||
|
@ -41,6 +53,13 @@ module Admin
|
|||
end
|
||||
end
|
||||
|
||||
def expire
|
||||
@price.expire
|
||||
@price.save!
|
||||
flash[:notice] = t('.expired')
|
||||
redirect_to_index
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def load_price
|
||||
|
@ -60,6 +79,13 @@ module Admin
|
|||
params.require(:price).permit(*allowed_params)
|
||||
end
|
||||
|
||||
def search_params
|
||||
allowed_params = %i[
|
||||
validity
|
||||
]
|
||||
params.fetch(:search, {}).permit(*allowed_params)
|
||||
end
|
||||
|
||||
def redirect_to_index
|
||||
redirect_to admin_prices_url
|
||||
end
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
module Billing
|
||||
class Price < ActiveRecord::Base
|
||||
include Versions
|
||||
include Concerns::Billing::Price::Expirable
|
||||
has_paper_trail class_name: '::PriceVersion'
|
||||
|
||||
self.auto_html5_validation = false
|
||||
|
@ -11,6 +12,7 @@ module Billing
|
|||
validates :operation_category, inclusion: { in: Proc.new { |price| price.class.operation_categories } }
|
||||
validates :duration, inclusion: { in: Proc.new { |price| price.class.durations } }
|
||||
|
||||
alias_attribute :expire_time, :valid_to
|
||||
monetize :price_cents, allow_nil: true, numericality: { greater_than_or_equal_to: 0 }
|
||||
after_initialize :init_values
|
||||
|
||||
|
|
21
app/models/concerns/billing/price/expirable.rb
Normal file
21
app/models/concerns/billing/price/expirable.rb
Normal file
|
@ -0,0 +1,21 @@
|
|||
module Concerns::Billing::Price::Expirable
|
||||
extend ActiveSupport::Concern
|
||||
|
||||
class_methods do
|
||||
def unexpired
|
||||
where("#{attribute_alias(:expire_time)} >= ?", Time.zone.now)
|
||||
end
|
||||
|
||||
def expired
|
||||
where("#{attribute_alias(:expire_time)} < ?", Time.zone.now)
|
||||
end
|
||||
end
|
||||
|
||||
def expire
|
||||
self[:valid_to] = Time.zone.now - 1
|
||||
end
|
||||
|
||||
def expired?
|
||||
expire_time.past?
|
||||
end
|
||||
end
|
|
@ -1,5 +1,5 @@
|
|||
<tr>
|
||||
<td><%= link_to price.zone_name, edit_admin_price_path(price), id: 'admin-edit-price-btn' %></td>
|
||||
<tr class="price">
|
||||
<td><%= link_to price.zone_name, edit_admin_price_path(price), class: 'edit-price-btn' %></td>
|
||||
<td><%= price.duration.sub('mons', 'months') %></td>
|
||||
<td><%= price.operation_category %></td>
|
||||
<td><%= number_to_currency price.price %></td>
|
||||
|
|
20
app/views/admin/billing/prices/_search_form.html.erb
Normal file
20
app/views/admin/billing/prices/_search_form.html.erb
Normal file
|
@ -0,0 +1,20 @@
|
|||
<%= form_for :search, url: admin_prices_path, method: :get, html: { class: 'form-horizontal' } do |f| %>
|
||||
<div class="form-group">
|
||||
<%= f.label :validity, class: 'col-sm-2 control-label' %>
|
||||
|
||||
<div class="col-sm-3">
|
||||
<%= f.select :validity, options_for_select(%w[unexpired expired], search.validity),
|
||||
{ include_blank: true },
|
||||
class: 'form-control' %>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<div class="col-sm-offset-2 col-sm-8">
|
||||
<%= f.submit t('.search_btn'), class: 'btn btn-primary', name: nil %>
|
||||
<%= link_to t('.reset_btn'), admin_prices_path,
|
||||
class: 'btn btn-default price-search-form-search-btn' %>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<% end %>
|
|
@ -3,7 +3,18 @@
|
|||
</ol>
|
||||
|
||||
<div class="page-header">
|
||||
<h1><%= t '.title' %></h1>
|
||||
<div class="row">
|
||||
<div class="col-sm-10">
|
||||
<h1><%= t '.title' %></h1>
|
||||
</div>
|
||||
|
||||
<div class="col-sm-2 text-right">
|
||||
<%= link_to(t('.expire_btn'), expire_admin_price_path(@price),
|
||||
method: :patch,
|
||||
data: { confirm: t('.expire_btn_confirm') },
|
||||
class: 'btn btn-danger') %>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<% if @price.persisted? && @price.errors.none? %>
|
||||
|
|
|
@ -10,6 +10,8 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<%= render 'search_form', search: @search %>
|
||||
|
||||
<% if @prices.present? %>
|
||||
<table class="table table-hover table-bordered table-wrapped">
|
||||
<thead>
|
||||
|
|
|
@ -15,10 +15,19 @@ en:
|
|||
|
||||
edit:
|
||||
title: Edit price
|
||||
expire_btn: Expire
|
||||
expire_btn_confirm: Are you sure you want to expire price?
|
||||
|
||||
update:
|
||||
updated: Price has been updated
|
||||
|
||||
expire:
|
||||
expired: Price has been expired
|
||||
|
||||
form:
|
||||
create_btn: Create price
|
||||
update_btn: Update price
|
||||
|
||||
search_form:
|
||||
search_btn: Search
|
||||
reset_btn: Reset
|
||||
|
|
|
@ -166,7 +166,13 @@ Rails.application.routes.draw do
|
|||
resources :zones, controller: 'dns/zones', except: %i[show destroy]
|
||||
resources :legal_documents
|
||||
resources :keyrelays
|
||||
resources :prices, controller: 'billing/prices', except: %i[show destroy]
|
||||
|
||||
resources :prices, controller: 'billing/prices', except: %i[show destroy] do
|
||||
member do
|
||||
patch :expire
|
||||
end
|
||||
end
|
||||
|
||||
resources :mail_templates
|
||||
resources :account_activities
|
||||
|
||||
|
|
|
@ -6,5 +6,13 @@ FactoryGirl.define do
|
|||
duration '1 year'
|
||||
operation_category Billing::Price.operation_categories.first
|
||||
zone
|
||||
|
||||
factory :unexpired_price do
|
||||
expire_time { Time.zone.now + 1.day }
|
||||
end
|
||||
|
||||
factory :expired_price do
|
||||
expire_time { Time.zone.now - 1.day }
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,24 +1,22 @@
|
|||
require 'rails_helper'
|
||||
|
||||
RSpec.feature 'Editing price in admin area', settings: false do
|
||||
given!(:price) { create(:price) }
|
||||
given!(:price) { create(:unexpired_price) }
|
||||
|
||||
background do
|
||||
sign_in_to_admin_area
|
||||
end
|
||||
|
||||
scenario 'updates price' do
|
||||
visit admin_prices_url
|
||||
visit admin_prices_path
|
||||
open_form
|
||||
submit_form
|
||||
|
||||
expect(page).to have_text(t('admin.billing.prices.update.updated'))
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def open_form
|
||||
click_link_or_button 'admin-edit-price-btn'
|
||||
find('.edit-price-btn').click
|
||||
end
|
||||
|
||||
def submit_form
|
||||
|
|
25
spec/features/admin/billing/prices/expire_spec.rb
Normal file
25
spec/features/admin/billing/prices/expire_spec.rb
Normal file
|
@ -0,0 +1,25 @@
|
|||
require 'rails_helper'
|
||||
|
||||
RSpec.feature 'Expiring price in admin area', settings: false do
|
||||
given!(:price) { create(:unexpired_price) }
|
||||
|
||||
background do
|
||||
sign_in_to_admin_area
|
||||
end
|
||||
|
||||
scenario 'expires price' do
|
||||
visit admin_prices_path
|
||||
open_edit_form
|
||||
expire
|
||||
|
||||
expect(page).to have_text(t('admin.billing.prices.expire.expired'))
|
||||
end
|
||||
|
||||
def open_edit_form
|
||||
find('.edit-price-btn').click
|
||||
end
|
||||
|
||||
def expire
|
||||
click_link_or_button t('admin.billing.prices.edit.expire_btn')
|
||||
end
|
||||
end
|
33
spec/features/admin/billing/prices/list_spec.rb
Normal file
33
spec/features/admin/billing/prices/list_spec.rb
Normal file
|
@ -0,0 +1,33 @@
|
|||
require 'rails_helper'
|
||||
|
||||
RSpec.feature 'Viewing prices in admin area', settings: false do
|
||||
given!(:unexpired_price) { create(:unexpired_price) }
|
||||
given!(:expired_price) { create(:expired_price) }
|
||||
|
||||
background do
|
||||
sign_in_to_admin_area
|
||||
end
|
||||
|
||||
describe 'search' do
|
||||
context 'when validity is not selected' do
|
||||
scenario 'shows unexpired prices' do
|
||||
visit admin_prices_path
|
||||
expect(page).to have_css('.price', count: 1)
|
||||
end
|
||||
end
|
||||
|
||||
context 'when validity is given' do
|
||||
scenario 'filters by given validity' do
|
||||
visit admin_prices_path
|
||||
select 'unexpired', from: 'search_validity'
|
||||
submit_search_form
|
||||
|
||||
expect(page).to have_css('.price', count: 1)
|
||||
end
|
||||
end
|
||||
|
||||
def submit_search_form
|
||||
find('.price-search-form-search-btn').click
|
||||
end
|
||||
end
|
||||
end
|
|
@ -16,8 +16,6 @@ RSpec.feature 'New price in admin area', settings: false do
|
|||
expect(page).to have_text(t('admin.billing.prices.create.created'))
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def open_list
|
||||
click_link_or_button t('admin.menu.prices')
|
||||
end
|
||||
|
|
|
@ -3,6 +3,7 @@ require 'rails_helper'
|
|||
RSpec.describe Billing::Price do
|
||||
it { is_expected.to monetize(:price) }
|
||||
it { is_expected.to be_versioned }
|
||||
it { is_expected.to alias_attribute(:expire_time, :valid_to) }
|
||||
|
||||
it 'should have one version' do
|
||||
with_versioning do
|
||||
|
|
69
spec/models/concerns/billing/price/expirable_spec.rb
Normal file
69
spec/models/concerns/billing/price/expirable_spec.rb
Normal file
|
@ -0,0 +1,69 @@
|
|||
require 'rails_helper'
|
||||
|
||||
RSpec.describe Billing::Price do
|
||||
describe '::unexpired' do
|
||||
before :example do
|
||||
travel_to Time.zone.parse('05.07.2010 00:00')
|
||||
|
||||
create(:price, id: 1, expire_time: Time.zone.parse('04.07.2010 23:59'))
|
||||
create(:price, id: 2, expire_time: Time.zone.parse('05.07.2010 00:00'))
|
||||
create(:price, id: 3, expire_time: Time.zone.parse('05.07.2010 00:01'))
|
||||
end
|
||||
|
||||
it 'returns prices with expire time in the future ' do
|
||||
expect(described_class.unexpired.ids).to eq([2, 3])
|
||||
end
|
||||
end
|
||||
|
||||
describe '::expired' do
|
||||
before :example do
|
||||
travel_to Time.zone.parse('05.07.2010 00:00')
|
||||
|
||||
create(:price, id: 1, expire_time: Time.zone.parse('04.07.2010 23:59'))
|
||||
create(:price, id: 2, expire_time: Time.zone.parse('05.07.2010 00:00'))
|
||||
create(:price, id: 3, expire_time: Time.zone.parse('05.07.2010 00:01'))
|
||||
end
|
||||
|
||||
it 'returns prices with expire time in the past ' do
|
||||
expect(described_class.expired.ids).to eq([1])
|
||||
end
|
||||
end
|
||||
|
||||
describe '#expire', db: false do
|
||||
let(:price) { described_class.new(expire_time: Time.zone.parse('06.07.2010')) }
|
||||
|
||||
before :example do
|
||||
travel_to Time.zone.parse('05.07.2010 00:00')
|
||||
end
|
||||
|
||||
it 'expires price' do
|
||||
expect { price.expire }.to change { price.expired? }.from(false).to(true)
|
||||
end
|
||||
end
|
||||
|
||||
describe '#expired?', db: false do
|
||||
subject(:expired) { domain.expired? }
|
||||
|
||||
before :example do
|
||||
travel_to Time.zone.parse('05.07.2010 00:00')
|
||||
end
|
||||
|
||||
context 'when expire time is in the past' do
|
||||
let(:domain) { described_class.new(expire_time: Time.zone.parse('04.07.2010 23:59')) }
|
||||
|
||||
specify { expect(expired).to be true }
|
||||
end
|
||||
|
||||
context 'when expire time is now' do
|
||||
let(:domain) { described_class.new(expire_time: Time.zone.parse('05.07.2010 00:00')) }
|
||||
|
||||
specify { expect(expired).to be false }
|
||||
end
|
||||
|
||||
context 'when expire time is in the future' do
|
||||
let(:domain) { described_class.new(expire_time: Time.zone.parse('05.07.2010 00:01')) }
|
||||
|
||||
specify { expect(expired).to be false }
|
||||
end
|
||||
end
|
||||
end
|
22
spec/requests/admin/billing/prices/expire_spec.rb
Normal file
22
spec/requests/admin/billing/prices/expire_spec.rb
Normal file
|
@ -0,0 +1,22 @@
|
|||
require 'rails_helper'
|
||||
|
||||
RSpec.describe 'admin price expire', settings: false do
|
||||
before :example do
|
||||
sign_in_to_admin_area
|
||||
end
|
||||
|
||||
it 'expires price' do
|
||||
price = create(:unexpired_price)
|
||||
|
||||
expect { patch expire_admin_price_path(price); price.reload }
|
||||
.to change { price.expired? }.from(false).to(true)
|
||||
end
|
||||
|
||||
it 'redirects to :index' do
|
||||
price = create(:unexpired_price)
|
||||
|
||||
patch expire_admin_price_path(price)
|
||||
|
||||
expect(response).to redirect_to admin_prices_url
|
||||
end
|
||||
end
|
Loading…
Add table
Add a link
Reference in a new issue