From b9a2a80a7525f0bf80496128c63c5b215a2a2492 Mon Sep 17 00:00:00 2001 From: Rob Smith Date: Fri, 9 Oct 2015 22:28:45 -0700 Subject: [PATCH] Support JSONP exports of conference schedules for embedding Currently, it's rather difficult to use OSEM and embed a schedule into another website. We currently use OSEM for the backend, but still use a different system for our main site. This change allows us to dynamically embed the schedule in our main website as well as allow us a simple way to get data for the use in mobile applications or similar. This limits the JSONP support to only GETS on json formatted requests. This prevents any XSS even though we don't require a authenticity token. --- app/controllers/conference_controller.rb | 12 +++++ app/models/conference.rb | 67 ++++++++++++++++++++++++ app/serializers/conference_serializer.rb | 4 +- 3 files changed, 82 insertions(+), 1 deletion(-) diff --git a/app/controllers/conference_controller.rb b/app/controllers/conference_controller.rb index 3ba355fd..90ba4c05 100644 --- a/app/controllers/conference_controller.rb +++ b/app/controllers/conference_controller.rb @@ -1,6 +1,13 @@ class ConferenceController < ApplicationController before_filter :respond_to_options load_and_authorize_resource find_by: :short_title + skip_before_filter :verify_authenticity_token, if: :json_request? + + def json_request? + return false if request.request_method != 'GET' + return false if !request.format.json? + true + end def index @current = Conference.where('end_date >= ?', Date.current).order('start_date ASC') @@ -19,6 +26,11 @@ class ConferenceController < ApplicationController else @today = @conference.start_date.strftime('%Y-%m-%d') end + + respond_to do |format| + format.html + format.json { render json: @conference.as_json, callback: params[:callback] } + end end def gallery_photos diff --git a/app/models/conference.rb b/app/models/conference.rb index 3c6f20b2..36787d5e 100644 --- a/app/models/conference.rb +++ b/app/models/conference.rb @@ -131,6 +131,73 @@ class Conference < ActiveRecord::Base result end + ## + # Builds out the model for returning a json response + # + # + def as_json(_options={}) + super( + only: [ + :description, + :end_date, + :logo, + :short_title, + :start_date, + :title, + ], + include: { + difficulty_levels: { + only: [ + :description, + :id, + :title, + ] + }, + event_types: { + only: [ + :description, + :id, + :length, + :title, + ] + }, + rooms: { + only: [ + :name, + :size, + ], + include: { + events: { + only: [ + :abstract, + :description, + :difficulty_level_id, + :event_type_id, + :guid, + :is_highlight, + :require_registration, + :start_time, + :subtitle, + :title, + :track_id, + ], + methods: [ + :speaker_names, + ], + }, + }, + }, + tracks: { + only: [ + :description, + :id, + :name, + ] + }, + } + ) + end + ## # Checks if the user is registered to the conference # diff --git a/app/serializers/conference_serializer.rb b/app/serializers/conference_serializer.rb index 1566e9da..77112cc3 100644 --- a/app/serializers/conference_serializer.rb +++ b/app/serializers/conference_serializer.rb @@ -20,7 +20,9 @@ class ConferenceSerializer < ActiveModel::Serializer # FIXME: adjusting the format the DIRTY way, for oSC13. # If you think this is ugly, don't look at the methods below def date_range - object.date_range_string.try(:split, ',').try(:first) + if defined? object.date_range_string + object.date_range_string.try(:split, ',').try(:first) + end end # FIXME: just giving suseconferenceclient something to play with