diff --git a/.haml-lint_todo.yml b/.haml-lint_todo.yml index acefafb1..a6dfa7c2 100644 --- a/.haml-lint_todo.yml +++ b/.haml-lint_todo.yml @@ -83,7 +83,6 @@ linters: - "app/views/admin/questions/index.html.haml" - "app/views/admin/questions/show.html.haml" - "app/views/admin/registration_periods/_form.html.haml" - - "app/views/admin/registration_periods/show.html.haml" - "app/views/admin/registrations/_questions.html.haml" - "app/views/admin/registrations/edit.html.haml" - "app/views/admin/registrations/index.csv.haml" @@ -242,8 +241,6 @@ linters: - "app/views/surveys/index.html.haml" - "app/views/surveys/show.html.haml" - "app/views/ticket_purchases/index.html.haml" - - "app/views/tickets/_ticket.html.haml" - - "app/views/tickets/index.html.haml" - "app/views/tracks/_form.html.haml" - "app/views/tracks/index.html.haml" - "app/views/tracks/show.html.haml" @@ -359,7 +356,6 @@ linters: - "app/views/admin/questions/index.html.haml" - "app/views/admin/questions/show.html.haml" - "app/views/admin/registration_periods/_form.html.haml" - - "app/views/admin/registration_periods/show.html.haml" - "app/views/admin/registrations/edit.html.haml" - "app/views/admin/registrations/index.html.haml" - "app/views/admin/reports/_all_events.html.haml" @@ -467,8 +463,6 @@ linters: - "app/views/surveys/_list.html.haml" - "app/views/surveys/index.html.haml" - "app/views/surveys/show.html.haml" - - "app/views/tickets/_ticket.html.haml" - - "app/views/tickets/index.html.haml" - "app/views/tracks/_form.html.haml" - "app/views/tracks/index.html.haml" - "app/views/tracks/show.html.haml" @@ -560,7 +554,6 @@ linters: - "app/views/shared/_media_item.html.haml" - "app/views/shared/_media_items.html.haml" - "app/views/tickets/_ticket.html.haml" - - "app/views/tickets/index.html.haml" - "app/views/tracks/index.html.haml" - "app/views/tracks/show.html.haml" @@ -603,7 +596,6 @@ linters: - "app/views/proposals/show.html.haml" - "app/views/schedules/events.html.haml" - "app/views/schedules/show.xml.haml" - - "app/views/tickets/index.html.haml" # Offense count: 2 FinalNewline: @@ -642,7 +634,6 @@ linters: - "app/views/conference_registrations/_volunteer.html.haml" - "app/views/devise/passwords/new.html.haml" - "app/views/payments/new.html.haml" - - "app/views/tickets/index.html.haml" # Offense count: 13 diff --git a/.rubocop_todo.yml b/.rubocop_todo.yml index 9929b1c2..297e6a27 100644 --- a/.rubocop_todo.yml +++ b/.rubocop_todo.yml @@ -1094,7 +1094,6 @@ Style/EmptyLiteral: Style/EmptyMethod: Exclude: - 'app/controllers/admin/lodgings_controller.rb' - - 'app/controllers/admin/registration_periods_controller.rb' - 'app/controllers/users_controller.rb' - 'db/migrate/20121223115125_create_tracks_table.rb' - 'db/migrate/20121223115135_create_events_table.rb' diff --git a/app/controllers/admin/registration_periods_controller.rb b/app/controllers/admin/registration_periods_controller.rb index 962c1027..d0884719 100644 --- a/app/controllers/admin/registration_periods_controller.rb +++ b/app/controllers/admin/registration_periods_controller.rb @@ -23,12 +23,6 @@ module Admin end end - def edit - end - - def show - end - def update @registration_period.assign_attributes(registration_period_params) send_mail_on_reg_update = @conference.notify_on_registration_dates_changed? diff --git a/app/controllers/ticket_purchases_controller.rb b/app/controllers/ticket_purchases_controller.rb index dac4e34f..632a7289 100644 --- a/app/controllers/ticket_purchases_controller.rb +++ b/app/controllers/ticket_purchases_controller.rb @@ -16,9 +16,11 @@ class TicketPurchasesController < ApplicationController elsif current_user.ticket_purchases.by_conference(@conference).paid.any? redirect_to conference_physical_tickets_path, notice: 'You have free tickets for the conference.' - else + elsif @conference.tickets.for_registration.any? redirect_to conference_tickets_path(@conference.short_title), error: 'Please get at least one ticket to continue.' + else + redirect_to conference_conference_registration_path(@conference.short_title) end else redirect_to conference_tickets_path(@conference.short_title), diff --git a/app/models/admin_ability.rb b/app/models/admin_ability.rb index c0328212..19d6c4d3 100644 --- a/app/models/admin_ability.rb +++ b/app/models/admin_ability.rb @@ -117,10 +117,7 @@ class AdminAbility can :manage, Commercial, commercialable_type: 'Conference', commercialable_id: conf_ids can :manage, Registration, conference_id: conf_ids - can :manage, RegistrationPeriod do |registration_period| - conference = registration_period.conference - conf_ids.include?(conference.id) && conference.tickets.for_registration.any? - end + can :manage, RegistrationPeriod, conference_id: conf_ids can :manage, Booth, conference_id: conf_ids can :manage, Question, conference_id: conf_ids can :manage, Question do |question| diff --git a/app/models/conference.rb b/app/models/conference.rb index dea75887..94484425 100644 --- a/app/models/conference.rb +++ b/app/models/conference.rb @@ -29,11 +29,7 @@ class Conference < ApplicationRecord has_many :ticket_purchases, dependent: :destroy has_many :payments, dependent: :destroy has_many :supporters, through: :ticket_purchases, source: :user - has_many :tickets, dependent: :destroy do - def for_registration - where(registration_ticket: true) - end - end + has_many :tickets, dependent: :destroy has_many :resources, dependent: :destroy has_many :booths, dependent: :destroy has_many :confirmed_booths, -> { where(state: 'confirmed') }, class_name: 'Booth' diff --git a/app/models/ticket.rb b/app/models/ticket.rb index 8553ebca..677ef90f 100644 --- a/app/models/ticket.rb +++ b/app/models/ticket.rb @@ -10,6 +10,8 @@ class Ticket < ApplicationRecord monetize :price_cents, with_model_currency: :price_currency + scope :for_registration, -> { where(registration_ticket: true) } + # This validation is for the sake of simplicity. # If we would allow different currencies per conference we also have to handle convertions between currencies! validate :tickets_of_conference_have_same_currency diff --git a/app/views/admin/registration_periods/show.html.haml b/app/views/admin/registration_periods/show.html.haml index 243220ec..51bc8d37 100644 --- a/app/views/admin/registration_periods/show.html.haml +++ b/app/views/admin/registration_periods/show.html.haml @@ -8,29 +8,38 @@ .row .col-md-8 %dl.dl-horizontal - %dt - Start Date - %dd - = @registration_period.start_date - %dt - End Date - %dd - = @registration_period.end_date + %dt Start Date + %dd= @registration_period.start_date + %dt End Date + %dd= @registration_period.end_date + %dt Ticket required? + %dd= @conference.tickets.for_registration.any? ? 'Yes' : 'No' + +.row + .col-md-12 + %p + If you would like to require a ticket purchase for registration, at least + one + = link_to 'ticket', admin_conference_tickets_path(@conference) + must be set as a registration ticket, and the registration process + will not proceed without the purchase (or selection of a free) single + registration ticket. + %p + To make ticketing optional, do not mark any + = link_to 'tickets', admin_conference_tickets_path(@conference) + as registration tickets, and registration can proceed without them. .row .col-md-12.text-right - - if @registration_period - - if can? :update, @registration_period - = link_to 'Edit', edit_admin_conference_registration_period_path, class: 'btn btn-primary' - - if can? :destroy, @registration_period - = link_to 'Delete', admin_conference_registration_period_path, - method: :delete, data: { confirm: 'Are you sure?' }, class: 'btn btn-danger' - - else - - if @conference.tickets.for_registration.empty? - .h3.text-left - No Registration Tickets! - %small - = link_to 'Create registration tickets', new_admin_conference_ticket_path - before creating the registration period. - - else - - if can? :create, @conference.build_registration_period - = link_to 'New Registration Period', new_admin_conference_registration_period_path, class: 'btn btn-primary' + .btn-group{ role: 'group' } + - if @registration_period + - if can? :update, @registration_period + = link_to 'Edit', edit_admin_conference_registration_period_path, + class: 'btn btn-primary' + - if can? :destroy, @registration_period + = link_to 'Delete', admin_conference_registration_period_path, + method: :delete, data: { confirm: 'Are you sure?' }, + class: 'btn btn-danger' + - elsif can? :create, @conference.build_registration_period + = link_to 'New Registration Period', + new_admin_conference_registration_period_path, + class: 'btn btn-primary' diff --git a/app/views/conference_registrations/show.html.haml b/app/views/conference_registrations/show.html.haml index 79e4b4fd..afb5b9e0 100644 --- a/app/views/conference_registrations/show.html.haml +++ b/app/views/conference_registrations/show.html.haml @@ -97,37 +97,48 @@ - if @conference.tickets.any? .row .col-md-12 - -if @tickets.any? - %h4 - %span.fa-stack - %i.fa.fa-square-o.fa-stack-2x - %i.fa.fa-ticket.fa-stack-1x - Ticket Purchases - = "(#{@tickets.first.price.symbol}#{humanized_money @total_price})" - %ul - .col-md-12 - - @ticket_payments.each_pair do |ticket_id, tickets| - %li - = @total_quantity[ticket_id] - = tickets.first.title - = word_pluralize(@total_quantity[ticket_id], 'Ticket') - for - = tickets.first.price.symbol - = humanized_money @total_price_per_ticket[ticket_id] - %br + %h4 + %span.fa-stack + %i.fa.fa-square-o.fa-stack-2x + %i.fa.fa-ticket.fa-stack-1x + Tickets - if @tickets.any? - .btn-group - = link_to 'View all tickets', conference_physical_tickets_path(@conference.short_title), class: "btn btn-success" - = link_to 'Get more tickets', conference_tickets_path(@conference.short_title), class: "btn btn-default" + Total Purchased: + = "(#{@tickets.first.price.symbol}#{humanized_money @total_price})" + %ul + .col-md-12 + - @ticket_payments.each_pair do |ticket_id, tickets| + %li + = @total_quantity[ticket_id] + = tickets.first.title + = word_pluralize(@total_quantity[ticket_id], 'Ticket') + for + = tickets.first.price.symbol + = humanized_money @total_price_per_ticket[ticket_id] + %br + .btn-group{ role: 'group' } + = link_to 'View all tickets', + conference_physical_tickets_path(@conference.short_title), + class: 'btn btn-success' + = link_to 'Get more tickets', + conference_tickets_path(@conference.short_title), + class: 'btn btn-default' - else - You haven't bought any tickets. - = link_to 'Please get some tickets to support us!', conference_tickets_path(@conference.short_title) %p - (Your participation won't be valid without getting a registration ticket) + You haven't bought any tickets. + = link_to 'Please get some tickets to support us!', conference_tickets_path(@conference.short_title) + - if @conference.tickets.for_registration.any? + %p + %em + Your participation won't be valid without getting a + registration ticket. + = link_to 'Get tickets', + conference_tickets_path(@conference.short_title), + class: 'btn btn-default' .row .col-md-12 - -if @registration + - if @registration .btn-group-vertical.pull-right = link_to 'Edit your Registration', edit_conference_conference_registration_path(@conference.short_title), class: 'btn btn-success', disabled: @conference.end_date < Date.today - if @tickets.any? diff --git a/app/views/tickets/_ticket.html.haml b/app/views/tickets/_ticket.html.haml index 726d836e..501e4151 100644 --- a/app/views/tickets/_ticket.html.haml +++ b/app/views/tickets/_ticket.html.haml @@ -2,18 +2,26 @@ %td.col-sm-8.col-md-4 .media .media-body - %h4.media-heading - = ticket.title - %h5.media-heading - - unless ticket.description.blank? - = markdown(ticket.description) - %td.col-sm-1.col-md-2.text-center - = ticket.registration_ticket? ? 'Yes' : 'No' + %h4.media-heading= ticket.title + %h5.media-heading= markdown(ticket.description) + - if @conference.tickets.for_registration.any? + %td.col-sm-1.col-md-2.text-center + = ticket.registration_ticket? ? 'Yes' : 'No' %td.col-sm-1.col-md-1 - - options = { type: 'number', min: 0, max: 99, class: "form-control quantity", 'data-id' => ticket.id } - - if ticket.registration_ticket? - - options[:max] = 1 - - options[:disabled] = current_user.tickets.for_registration(ticket.conference).present? + :ruby + options = { + type: 'number', + min: 0, + max: 99, + class: 'form-control quantity', + 'data-id' => ticket.id + } + if ticket.registration_ticket? + options[:max] = 1 + options[:disabled] = current_user.tickets.for_registration( + ticket.conference + ).present? + end = text_field_tag("tickets[][#{ticket.id}]", 0, options) %td.col-sm-1.col-md-1.text-center = ticket.price.symbol diff --git a/app/views/tickets/index.html.haml b/app/views/tickets/index.html.haml index cba13ea5..e157d75e 100644 --- a/app/views/tickets/index.html.haml +++ b/app/views/tickets/index.html.haml @@ -5,25 +5,26 @@ %h1 Tickets %p.lead - Please choose your tickets for + Please choose your tickets for %strong = @conference.title - here* - =form_tag(conference_ticket_purchases_path, method: :post) do |f| + = form_tag(conference_ticket_purchases_path, method: :post) do |f| %table.table.table-hover %thead %tr %th Ticket - %th Registration Ticket + - if @conference.tickets.for_registration.any? + %th Registration Ticket %th Quantity %th Price %th Total %tbody - @conference.tickets.each do |ticket| - = render partial: 'ticket', f: f, locals: {ticket: ticket} + = render 'ticket', f: f, ticket: ticket %tr %td - %td + - if @conference.tickets.for_registration.any? + %td %td %td.col-sm-1.col-md-1.text-center %h4 @@ -32,20 +33,20 @@ %h4 %strong = @conference.tickets.first.price.symbol - %span{id: 'total_price'} + %span{ id: 'total_price' } 0 .pull-right .btn-group-vertical = button_tag(type: 'submit', class: 'btn btn-success btn-lg') do Continue %i.fa.fa-shopping-cart - - if current_user.ticket_purchases.by_conference(@conference).any? - = link_to 'Back to registration', conference_conference_registration_path(@conference.short_title), class: 'btn btn-default btn-sm' - - else - = link_to 'Cancel registration', conference_conference_registration_path(@conference.short_title), method: :delete, class: 'btn btn-danger btn-sm', - data: { confirm: 'Are you sure you want to unregister?' } - .row - .col-md-13 - %p.text-muted.text-center - %small - * Getting a registration ticket is mandatory. Your participation will not be valid until you get a registration ticket. + = link_to 'Back to registration', + conference_conference_registration_path(@conference.short_title), + class: 'btn btn-default btn-sm' + - if @conference.tickets.for_registration.any? + .row + .col-md-13 + %p.text-muted.text-center + %small + Getting a registration ticket is mandatory. Your participation + will not be valid until you get a registration ticket. diff --git a/spec/features/registration_periods_spec.rb b/spec/features/registration_periods_spec.rb index 89af9a4e..de94f7bb 100644 --- a/spec/features/registration_periods_spec.rb +++ b/spec/features/registration_periods_spec.rb @@ -3,19 +3,22 @@ require 'spec_helper' feature RegistrationPeriod do - # It is necessary to use bang version of let to build roles before user let!(:conference) { create(:conference) } let!(:organizer_role) { Role.find_by(name: 'organizer', resource: conference) } let!(:organizer) { create(:user, email: 'admin@example.com', role_ids: [organizer_role.id]) } - let!(:registration_ticket) { create(:registration_ticket, conference: conference) } + let(:start_date) { Date.today } + let(:end_date) { Date.today + 5 } - shared_examples 'successfully' do - scenario 'create and update registration period', js: true do + context 'as organizer' do + before do sign_in organizer - visit admin_conference_registration_period_path( - conference_id: conference.short_title) + visit admin_conference_registration_period_path(conference_id: conference) + click_link 'New Registration Period' + end + scenario 'requires start date and end date', feature: true do + visit admin_conference_registration_period_path(conference_id: conference) click_link 'New Registration Period' click_button 'Save Registration Period' @@ -23,27 +26,54 @@ feature RegistrationPeriod do expect(flash) .to eq('An error prohibited the Registration Period from being saved: ' \ "Start date can't be blank. End date can't be blank.") - page.find('#flash .close').click - page - .execute_script("$('#registration-period-start-datepicker').val('" + - "#{Date.today.strftime('%d/%m/%Y')}')") - page - .execute_script("$('#registration-period-end-datepicker').val('" + - "#{(Date.today + 5).strftime('%d/%m/%Y')}')") + end - click_button 'Save Registration Period' - page.find('#flash') - expect(flash).to eq('Registration Period successfully updated.') - expect(current_path).to eq(admin_conference_registration_period_path(conference.short_title)) + context 'with tickets' do + let!(:registration_ticket) do + create(:registration_ticket, conference: conference) + end - registration_period = RegistrationPeriod.where(conference_id: conference.id).first - registration_period.reload - expect(registration_period.start_date).to eq(Date.today) - expect(registration_period.end_date).to eq(Date.today + 5) + it 'creates registration period', feature: true, js: true do + page + .execute_script("$('#registration-period-start-datepicker').val('" + + "#{start_date.strftime('%d/%m/%Y')}')") + page + .execute_script("$('#registration-period-end-datepicker').val('" + + "#{end_date.strftime('%d/%m/%Y')}')") + + click_button 'Save Registration Period' + page.find('#flash') + expect(flash).to eq('Registration Period successfully updated.') + expect(current_path).to eq(admin_conference_registration_period_path(conference.short_title)) + expect(page).to have_text("Ticket required?\nYes") + + registration_period = RegistrationPeriod.where(conference_id: conference.id).first + registration_period.reload + expect(registration_period.start_date).to eq(start_date) + expect(registration_period.end_date).to eq(end_date) + end + end + + context 'without tickets' do + it 'creates registration period', feature: true, js: true do + page + .execute_script("$('#registration-period-start-datepicker').val('" + + "#{start_date.strftime('%d/%m/%Y')}')") + page + .execute_script("$('#registration-period-end-datepicker').val('" + + "#{end_date.strftime('%d/%m/%Y')}')") + + click_button 'Save Registration Period' + page.find('#flash') + expect(flash).to eq('Registration Period successfully updated.') + expect(current_path).to eq(admin_conference_registration_period_path(conference.short_title)) + expect(page).to have_text("Ticket required?\nNo") + + registration_period = RegistrationPeriod.where(conference_id: conference.id).first + registration_period.reload + expect(registration_period.start_date).to eq(start_date) + expect(registration_period.end_date).to eq(end_date) + end end end - - describe 'organizer' do - it_behaves_like 'successfully' - end end