Skip to content

Commit

Permalink
Allow admin to create & edit events
Browse files Browse the repository at this point in the history
  • Loading branch information
luciagirasoles committed Sep 26, 2023
1 parent 6b8948c commit 57c808a
Show file tree
Hide file tree
Showing 37 changed files with 484 additions and 62 deletions.
5 changes: 4 additions & 1 deletion app/assets/stylesheets/admin.bootstrap.scss
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@

@import 'admin/components/colors.scss';
@import 'admin/components/buttons.scss';

Expand All @@ -8,3 +7,7 @@

// Custom
@import 'admin/header.scss';

// Slim Select custom
@import 'slim-select/dist/slimselect.css';
@import 'admin/custom_slim_select.scss';
36 changes: 36 additions & 0 deletions app/assets/stylesheets/admin/custom_slim_select.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
.ss-content {
padding-right: 0.75rem;
background-image: none;

.ss-list {
height: 150px;

.ss-option {
color: var(--bs-body-color);

&:not(.ss-disabled) {
&.ss-selected {
background-color: $primary;
}

&:first-child {
color: var(--bs-secondary-color);
}
}

&:hover {
color: var(--bs-body-color);
background-color: $primary;
}
&:first-child {
&.ss-selected {
background-color: $primary-bg-subtle;
}
}
}
}

.ss-search input:focus {
box-shadow: $box-shadow-sm;
}
}
53 changes: 48 additions & 5 deletions app/controllers/admin/events_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ def create
@event = Event.create(event_params)

if @event.save
redirect_to admin_events_path, notice: 'Event has been created successfully'
redirect_to edit_admin_event_path(@event), notice: 'Event was successfully created'
else
render :new, alert: 'Please review'
render :new, status: :unprocessable_entity
end
end

Expand All @@ -30,9 +30,9 @@ def update
render_not_found unless @event

if @event.update(event_params)
redirect_to admin_events_path
redirect_to admin_events_path, notice: 'Event was successfully updated'
else
render :edit
render :edit, notice: 'Error updating event'
end
end

Expand All @@ -46,24 +46,67 @@ def destroy
end
end

#GET /admin/events/set_talk/1
def set_talk
@talk = Talk.new
@url = generate_talk_admin_events_path(talk_id: 'create_talk')

return unless params[:talk_id] != 'new_talk'
talk_id = params[:talk_id]
@talk = Talk.new(event_params['talks_attributes'][talk_id].except(:_destroy))
@url = generate_talk_admin_events_path(talk_id: talk_id)

end

#POST /admin/events/get_talk/1
def generate_talk
@talk = Talk.new(talk_params)
talk_id = @talk.object_id

if params[:talk_id] != 'create_talk'
talk_id = params[:talk_id]
@talk.id = params[:talk_id]
end

if @talk.valid?
render 'admin/events/form/_card_talk_new', locals: { talk: @talk, talk_id: talk_id }
else
@url = generate_talk_admin_events_path(talk_id: talk_id)
render :set_talk, status: :bad_request
end
end

private

def authorize_event
authorize Event
end

def set_event
@event = Event.includes(:talks).find_by(id: params[:id])
@event = Event.includes(talks: :speaker).find_by(id: params[:id])
end

def event_params
params.require(:event).permit(
:id,
:title,
:location,
:description,
:date,
:type,
:panel_video_link,
talks_attributes: Talk.attribute_names.map(&:to_sym).push(:_destroy),
)
end

def talk_params
params.require(:talk).permit(
:talk_description,
:talk_title,
:talk_video_link,
:speaker_id,
:event_id,
:_destroy,
)
end
end
Expand Down
2 changes: 1 addition & 1 deletion app/controllers/admin/speakers_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ class SpeakersController < AdminController

# GET /admin/speakers
def index
@speakers = Speaker.ordered_by_name
@speakers = Speaker.all
end

# GET /admin/speakers/1
Expand Down
3 changes: 3 additions & 0 deletions app/javascript/admin.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,6 @@
import './controllers';
import * as bootstrap from 'bootstrap';
import '@hotwired/turbo-rails';
import './turbo_streams';

window.bootstrap = bootstrap;
15 changes: 15 additions & 0 deletions app/javascript/controllers/bs_modal_controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { Controller } from '@hotwired/stimulus';

// Connects to data-controller="bs-modal"
export default class extends Controller {
connect() {
// eslint-disable-next-line no-undef
this.modal = new bootstrap.Modal(this.element);

this.modal.show();
}

disconnect() {
this.modal.hide();
}
}
20 changes: 20 additions & 0 deletions app/javascript/controllers/event_form_remove_talk_controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import { Controller } from '@hotwired/stimulus';

// Connects to data-controller="event-form-remove-talk"
export default class extends Controller {
removeRecord(event) {
let talkId = event.currentTarget.dataset.talkId;
let talkPersisted = event.currentTarget.dataset.persisted === 'true';
let talk = document.getElementById(`talk-${talkId}`);
console.log(talkPersisted);

if (talkPersisted) {
console.log('to be hidden');
let removeRecordElement = talk.querySelector('.remove_record');
removeRecordElement.value = '1';
talk.className += ' d-none';
} else {
talk.remove();
}
}
}
12 changes: 12 additions & 0 deletions app/javascript/controllers/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,17 @@

import { application } from './application';

import BsModalController from './bs_modal_controller';
application.register('bs-modal', BsModalController);

import HelloController from './hello_controller';
application.register('hello', HelloController);

import EventFormRemoveTalkController from './event_form_remove_talk_controller';
application.register('event-form-remove-talk', EventFormRemoveTalkController);

import SlimSelectController from './slim_select_controller';
application.register('slim-select', SlimSelectController);

import TurboController from './turbo_controller';
application.register('turbo', TurboController);
19 changes: 19 additions & 0 deletions app/javascript/controllers/slim_select_controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import { Controller } from '@hotwired/stimulus';
import SlimSelect from 'slim-select';

// Connects to data-controller="slim-select"
export default class extends Controller {
connect() {
this.select = new SlimSelect({
select: this.element,
settings: {
openPosition: 'up',
},
});
document.querySelector('svg.ss-arrow').remove();
}

disconnect() {
this.select.destroy();
}
}
36 changes: 36 additions & 0 deletions app/javascript/controllers/turbo_controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
import { Controller } from '@hotwired/stimulus';
import { Turbo } from '@hotwired/turbo-rails';
// Connects to data-controller="turbo"
export default class extends Controller {
initialize() {
this.element.setAttribute('data-action', 'click->turbo#click');
}
click(e) {
e.preventDefault();

if (this.element.hasAttribute('href')) {
// If href is present, get its value
this.url = this.element.getAttribute('href');
} else if (this.element.hasAttribute('data-href')) {
// If href is not present, check for data-href attribute
this.url = this.element.getAttribute('data-href');
} else if (this.element.hasAttribute('formaction')) {
// If href is not present, check for formaction attribute
// breakpoint here

this.url = this.element.getAttribute('formaction');
}
if (this.url) {
fetch(this.url, {
headers: {
Accept: 'text/vnd.turbo-stream.html',
},
})
.then((r) => r.text())
.then((html) => Turbo.renderStreamMessage(html))
.catch((err) => console.log(err));
} else {
console.log('No URL found');
}
}
}
1 change: 1 addition & 0 deletions app/javascript/turbo_streams/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
import './update_children_or_append';
43 changes: 43 additions & 0 deletions app/javascript/turbo_streams/update_children_or_append.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
import { StreamActions } from '@hotwired/turbo';

StreamActions.update_children_or_append = function () {
// Custom duplicateChildren function
function duplicateChildren(existingChildren, newChildrenIds) {
return existingChildren
.filter((existingChild) => newChildrenIds.includes(existingChild.id))
.map((existingChild) => {
const templateChild = this.templateContent.querySelector(`#${existingChild.id}`);
return { targetChild: existingChild, templateChild };
});
}

// Check if the template content has any children
if (this.duplicateChildren.length > 0) {
// Get existing children with IDs
const existingChildren = this.targetElements
.flatMap((e) => [...e.children])
.filter((c) => !!c.id);

// Get new children IDs
const newChildrenIds = [...(this.templateContent?.children || [])]
.filter((c) => !!c.id)
.map((c) => c.id);

// Get the array of duplicated children with targetChild and templateChild properties using the custom function
const duplicatedChildren = duplicateChildren.call(this, existingChildren, newChildrenIds);

duplicatedChildren.forEach(({ targetChild, templateChild }) => {
if (targetChild && templateChild) {
const newElement = templateChild.cloneNode(true);
templateChild.remove();
targetChild.replaceWith(newElement);

// Access the new element here
// console.log(newElement);
}
});
} else {
// Append new children
this.targetElements.forEach((e) => e.append(this.templateContent));
}
};
2 changes: 2 additions & 0 deletions app/models/event.rb
Original file line number Diff line number Diff line change
Expand Up @@ -18,5 +18,7 @@ class Event < ApplicationRecord
has_many :talks, dependent: :destroy
has_many :speakers, through: :talks

accepts_nested_attributes_for :talks, allow_destroy: true

validates :title, :location, :date, presence: true
end
2 changes: 1 addition & 1 deletion app/models/speaker.rb
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ class Speaker < ApplicationRecord

before_validation :format_links

scope :ordered_by_name, -> { order(:name) }
default_scope { order(name: :asc) }

def validate_social_media_brand
return if links.blank? || links.keys.all? { |key| SOCIAL_MEDIA_LINKS.include?(key) }
Expand Down
6 changes: 5 additions & 1 deletion app/models/talk.rb
Original file line number Diff line number Diff line change
Expand Up @@ -25,5 +25,9 @@
#
class Talk < ApplicationRecord
belongs_to :speaker
belongs_to :event
belongs_to :event, optional: true

validates :talk_title, :talk_description, presence: true

default_scope { order(id: :asc) }
end
8 changes: 8 additions & 0 deletions app/policies/event_policy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,12 @@ def update?
def destroy?
user.admin?
end

def set_talk?
create?
end

def generate_talk?
create?
end
end
Loading

0 comments on commit 57c808a

Please sign in to comment.