From cf5a33f17d076135c4c431d61182c38d67d5bc20 Mon Sep 17 00:00:00 2001 From: Jan Werkhoven Date: Sun, 7 Apr 2024 22:41:46 +1000 Subject: [PATCH 1/3] Set default value for positional param in allow_create() --- app/controllers/concerns/json_api_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/concerns/json_api_controller.rb b/app/controllers/concerns/json_api_controller.rb index a739cd4..f7bdc89 100644 --- a/app/controllers/concerns/json_api_controller.rb +++ b/app/controllers/concerns/json_api_controller.rb @@ -391,7 +391,7 @@ def forbidden_filters # allow_create # end # - def allow_create(controller_attributes: nil) + def allow_create(controller_attributes = nil) hash = strong_attributes .merge(strong_relationships) .merge(controller_attributes) From ccd2fd21e13846f102216f0084467085d351d2c6 Mon Sep 17 00:00:00 2001 From: Jan Werkhoven Date: Sun, 7 Apr 2024 22:44:14 +1000 Subject: [PATCH 2/3] Add migrations, models and controllers for Event Attendees and forms --- .../v1/admin/event_attendees_controller.rb | 35 +++++++++++++ app/controllers/v1/admin/events_controller.rb | 10 ++++ .../v1/public/event_attendees_controller.rb | 51 +++++++++++++++++++ app/models/event.rb | 33 ++++++++---- app/models/event_attendee.rb | 19 +++++++ app/models/permalink.rb | 11 ++-- .../v1/admin/event_attendee_serializer.rb | 14 +++++ app/serializers/v1/admin/event_serializer.rb | 13 ++++- .../v1/admin/permalink_serializer.rb | 2 + .../v1/public/event_attendee_serializer.rb | 13 +++++ app/serializers/v1/public/event_serializer.rb | 7 ++- config/routes.rb | 2 + .../20240406020528_create_event_attendees.rb | 33 ++++++++++++ ...27_add_unique_constraints_to_permalinks.rb | 5 ++ db/schema.rb | 24 ++++++++- test/fixtures/events.yml | 39 +++++++------- 16 files changed, 274 insertions(+), 37 deletions(-) create mode 100644 app/controllers/v1/admin/event_attendees_controller.rb create mode 100644 app/controllers/v1/public/event_attendees_controller.rb create mode 100644 app/models/event_attendee.rb create mode 100644 app/serializers/v1/admin/event_attendee_serializer.rb create mode 100644 app/serializers/v1/public/event_attendee_serializer.rb create mode 100644 db/migrate/20240406020528_create_event_attendees.rb create mode 100644 db/migrate/20240407010227_add_unique_constraints_to_permalinks.rb diff --git a/app/controllers/v1/admin/event_attendees_controller.rb b/app/controllers/v1/admin/event_attendees_controller.rb new file mode 100644 index 0000000..a46f45b --- /dev/null +++ b/app/controllers/v1/admin/event_attendees_controller.rb @@ -0,0 +1,35 @@ +module V1 + module Admin + class EventAttendeesController < ApplicationController + def index + allow_index + end + + def show + allow_show + end + + def create + forbidden + end + + def update + forbidden + end + + def destroy + forbidden + end + + private + + def model_class + EventAttendee + end + + def serializer_class + V1::Admin::EventAttendeeSerializer + end + end + end +end diff --git a/app/controllers/v1/admin/events_controller.rb b/app/controllers/v1/admin/events_controller.rb index bac889e..f68b7b3 100644 --- a/app/controllers/v1/admin/events_controller.rb +++ b/app/controllers/v1/admin/events_controller.rb @@ -39,6 +39,14 @@ def creatable_attributes start_date end_date description + has_registration_form + ask_first_name + ask_last_name + ask_role + ask_company + confirmation_email_subject + confirmation_email_body + confirmation_email_bcc ] end @@ -51,6 +59,8 @@ def creatable_relationships def permitted_includes %i[ country + permalinks + event_attendees ] end end diff --git a/app/controllers/v1/public/event_attendees_controller.rb b/app/controllers/v1/public/event_attendees_controller.rb new file mode 100644 index 0000000..5b57459 --- /dev/null +++ b/app/controllers/v1/public/event_attendees_controller.rb @@ -0,0 +1,51 @@ +module V1 + module Public + class EventAttendeesController < ApplicationController + def index + forbidden + end + + def show + forbidden + end + + def create + allow_create + end + + def update + allow_update + end + + def destroy + forbidden + end + + private + + def model_class + EventAttendee + end + + def serializer_class + V1::Public::EventAttendeeSerializer + end + + def creatable_attributes + %i[ + first_name + last_name + role + company + email + ] + end + + def creatable_relationships + %i[ + event + ] + end + end + end +end diff --git a/app/models/event.rb b/app/models/event.rb index f7308a0..bc00e4d 100644 --- a/app/models/event.rb +++ b/app/models/event.rb @@ -2,17 +2,30 @@ # # Table name: events # -# id :uuid not null, primary key -# city :string -# dates :string -# description :string -# end_date :string -# name :string -# start_date :string -# created_at :datetime not null -# updated_at :datetime not null -# country_id :string +# id :uuid not null, primary key +# ask_company :boolean +# ask_first_name :boolean +# ask_last_name :boolean +# ask_role :boolean +# city :string +# confirmation_email_bcc :string default("s.teliszewski@interflux.com, jw@interflux.au") +# confirmation_email_body :string default("Hello {first_name} {last_name}, We look forward seeing you at {event_name} on {event_date} in {event_location}. Best regards, The Interflux Electronics team") +# confirmation_email_subject :string default("See you soon at {event_name}!") +# dates :string +# description :string +# end_date :string +# has_registration_form :boolean +# name :string +# start_date :string +# created_at :datetime not null +# updated_at :datetime not null +# country_id :string # class Event < ApplicationRecord belongs_to :country + + has_many :permalinks + has_many :event_attendees + + alias_attribute :attendees, :event_attendees end diff --git a/app/models/event_attendee.rb b/app/models/event_attendee.rb new file mode 100644 index 0000000..10660a2 --- /dev/null +++ b/app/models/event_attendee.rb @@ -0,0 +1,19 @@ +# == Schema Information +# +# Table name: event_attendees +# +# id :uuid not null, primary key +# company :string +# email :string +# first_name :string +# last_name :string +# role :string +# created_at :datetime not null +# updated_at :datetime not null +# event_id :uuid +# person_id :uuid +# +class EventAttendee < ApplicationRecord + belongs_to :event + belongs_to :person, optional: true +end diff --git a/app/models/permalink.rb b/app/models/permalink.rb index c8fa0fd..f9c43be 100644 --- a/app/models/permalink.rb +++ b/app/models/permalink.rb @@ -6,9 +6,14 @@ # notes :string # redirect_to :string # slug :string +# event_id :uuid +# +# Indexes +# +# index_permalinks_on_slug (slug) UNIQUE # class Permalink < ApplicationRecord - # attr :redirect_from - # attr :redirect_to - # attr :notes + belongs_to :event, optional: true + + validates :slug, presence: true, uniqueness: true end diff --git a/app/serializers/v1/admin/event_attendee_serializer.rb b/app/serializers/v1/admin/event_attendee_serializer.rb new file mode 100644 index 0000000..9eea2b0 --- /dev/null +++ b/app/serializers/v1/admin/event_attendee_serializer.rb @@ -0,0 +1,14 @@ +module V1 + module Admin + class EventAttendeeSerializer < ApplicationSerializer + attributes :first_name, + :last_name, + :role, + :company, + :email + + belongs_to :event + belongs_to :person + end + end +end diff --git a/app/serializers/v1/admin/event_serializer.rb b/app/serializers/v1/admin/event_serializer.rb index af1f074..c0f8dc0 100644 --- a/app/serializers/v1/admin/event_serializer.rb +++ b/app/serializers/v1/admin/event_serializer.rb @@ -6,9 +6,20 @@ class EventSerializer < ApplicationSerializer :dates, :start_date, :end_date, - :description + :description, + :has_registration_form, + :ask_first_name, + :ask_last_name, + :ask_role, + :ask_company, + :confirmation_email_subject, + :confirmation_email_body, + :confirmation_email_bcc belongs_to :country + + has_many :event_attendees + has_many :permalinks end end end diff --git a/app/serializers/v1/admin/permalink_serializer.rb b/app/serializers/v1/admin/permalink_serializer.rb index 13d1549..02536d8 100644 --- a/app/serializers/v1/admin/permalink_serializer.rb +++ b/app/serializers/v1/admin/permalink_serializer.rb @@ -4,6 +4,8 @@ class PermalinkSerializer < ApplicationSerializer attributes :slug, :redirect_to, :notes + + belongs_to :event end end end diff --git a/app/serializers/v1/public/event_attendee_serializer.rb b/app/serializers/v1/public/event_attendee_serializer.rb new file mode 100644 index 0000000..c5d4c6e --- /dev/null +++ b/app/serializers/v1/public/event_attendee_serializer.rb @@ -0,0 +1,13 @@ +module V1 + module Public + class EventAttendeeSerializer < ApplicationSerializer + attributes :first_name, + :last_name, + :role, + :company, + :email + + belongs_to :event + end + end +end diff --git a/app/serializers/v1/public/event_serializer.rb b/app/serializers/v1/public/event_serializer.rb index c3960c5..70fbde7 100644 --- a/app/serializers/v1/public/event_serializer.rb +++ b/app/serializers/v1/public/event_serializer.rb @@ -6,7 +6,12 @@ class EventSerializer < ApplicationSerializer :dates, :start_date, :end_date, - :description + :description, + :has_registration_form, + :ask_first_name, + :ask_last_name, + :ask_role, + :ask_company belongs_to :country end diff --git a/config/routes.rb b/config/routes.rb index f27e0f6..d6d7314 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -26,6 +26,7 @@ resources :document_categories, path: '/document-categories' resources :documents resources :events + resources :event_attendees, path: '/event-attendees' resources :features resources :images resources :languages @@ -69,6 +70,7 @@ resources :document_categories, path: '/document-categories' resources :documents resources :events + resources :event_attendees, path: '/event-attendees' resources :features resources :images resources :languages diff --git a/db/migrate/20240406020528_create_event_attendees.rb b/db/migrate/20240406020528_create_event_attendees.rb new file mode 100644 index 0000000..37a3087 --- /dev/null +++ b/db/migrate/20240406020528_create_event_attendees.rb @@ -0,0 +1,33 @@ +class CreateEventAttendees < ActiveRecord::Migration[6.1] + def change + change_table :events, bulk: true do |t| + t.column :has_registration_form, :boolean + + t.column :ask_first_name, :boolean + t.column :ask_last_name, :boolean + t.column :ask_role, :boolean + t.column :ask_company, :boolean + + t.column :confirmation_email_subject, :string, default: 'See you soon at {event_name}!' + t.column :confirmation_email_body, :string, default: 'Hello {first_name} {last_name}, We look forward seeing you at {event_name} on {event_date} in {event_location}. Best regards, The Interflux Electronics team' + t.column :confirmation_email_bcc, :string, default: 's.teliszewski@interflux.com, jw@interflux.au' + end + + change_table :permalinks, bulk: true do |t| + t.column :event_id, :uuid + end + + create_table :event_attendees, id: :uuid do |t| + t.uuid :event_id + t.uuid :person_id + + t.string :first_name + t.string :last_name + t.string :role + t.string :company + t.string :email + + t.timestamps + end + end +end diff --git a/db/migrate/20240407010227_add_unique_constraints_to_permalinks.rb b/db/migrate/20240407010227_add_unique_constraints_to_permalinks.rb new file mode 100644 index 0000000..a385f33 --- /dev/null +++ b/db/migrate/20240407010227_add_unique_constraints_to_permalinks.rb @@ -0,0 +1,5 @@ +class AddUniqueConstraintsToPermalinks < ActiveRecord::Migration[6.1] + def change + add_index :permalinks, :slug, unique: true + end +end diff --git a/db/schema.rb b/db/schema.rb index de92aef..ff63b77 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 2024_02_10_021903) do +ActiveRecord::Schema.define(version: 2024_04_07_010227) do # These are extensions that must be enabled in order to support this database enable_extension "pgcrypto" @@ -223,6 +223,18 @@ t.index ["person_id"], name: "index_employees_on_person_id" end + create_table "event_attendees", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t| + t.uuid "event_id" + t.uuid "person_id" + t.string "first_name" + t.string "last_name" + t.string "role" + t.string "company" + t.string "email" + t.datetime "created_at", precision: 6, null: false + t.datetime "updated_at", precision: 6, null: false + end + create_table "events", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t| t.string "name" t.string "description" @@ -233,6 +245,14 @@ t.datetime "updated_at", null: false t.string "start_date" t.string "end_date" + t.boolean "has_registration_form" + t.boolean "ask_first_name" + t.boolean "ask_last_name" + t.boolean "ask_role" + t.boolean "ask_company" + t.string "confirmation_email_subject", default: "See you soon at {event_name}!" + t.string "confirmation_email_body", default: "Hello {first_name} {last_name}, We look forward seeing you at {event_name} on {event_date} in {event_location}. Best regards, The Interflux Electronics team" + t.string "confirmation_email_bcc", default: "s.teliszewski@interflux.com, jw@interflux.au" end create_table "features", primary_key: "slug", id: :string, force: :cascade do |t| @@ -314,6 +334,8 @@ t.string "slug" t.string "redirect_to" t.string "notes" + t.uuid "event_id" + t.index ["slug"], name: "index_permalinks_on_slug", unique: true end create_table "person_images", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t| diff --git a/test/fixtures/events.yml b/test/fixtures/events.yml index 75d3384..7d4f287 100644 --- a/test/fixtures/events.yml +++ b/test/fixtures/events.yml @@ -2,25 +2,22 @@ # # Table name: events # -# id :uuid not null, primary key -# city :string -# dates :string -# description :string -# end_date :string -# name :string -# start_date :string -# created_at :datetime not null -# updated_at :datetime not null -# country_id :string +# id :uuid not null, primary key +# ask_company :boolean +# ask_first_name :boolean +# ask_last_name :boolean +# ask_role :boolean +# city :string +# confirmation_email_bcc :string default("s.teliszewski@interflux.com, jw@interflux.au") +# confirmation_email_body :string default("Hello {first_name} {last_name}, We look forward seeing you at {event_name} on {event_date} in {event_location}. Best regards, The Interflux Electronics team") +# confirmation_email_subject :string default("See you soon at {event_name}!") +# dates :string +# description :string +# end_date :string +# has_registration_form :boolean +# name :string +# start_date :string +# created_at :datetime not null +# updated_at :datetime not null +# country_id :string # -# event_fixture_1: -# name: Some Name -# slug: some-name -# public: true -# group: other_thing_fixture_1 -# -# event_fixture_2: -# name: Some Name -# slug: some-name -# public: true -# group: other_thing_fixture_1 From 8f54381423fb5819efc6debe221b1aeb684f6119 Mon Sep 17 00:00:00 2001 From: Jan Werkhoven Date: Sun, 7 Apr 2024 22:45:03 +1000 Subject: [PATCH 3/3] Create unique random slug if permalinks are created without --- .../v1/admin/permalinks_controller.rb | 30 ++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/app/controllers/v1/admin/permalinks_controller.rb b/app/controllers/v1/admin/permalinks_controller.rb index e28e5a5..ef5bee4 100644 --- a/app/controllers/v1/admin/permalinks_controller.rb +++ b/app/controllers/v1/admin/permalinks_controller.rb @@ -10,7 +10,11 @@ def show end def create - allow_create + allow_create( + { + slug: unique_slug + } + ) end def update @@ -39,11 +43,35 @@ def creatable_attributes ] end + def creatable_relationships + %i[ + event + ] + end + def permitted_filters %i[ slug ] end + + def unique_slug + slug = nil + unique = false + + until slug.present? && unique + slug = three_random_letters + record = Permalink.find_by slug: slug + unique = record.nil? + end + + slug + end + + def three_random_letters + charset = Array('A'..'Z') + Array('a'..'z') + Array.new(3) { charset.sample }.join + end end end end