require 'seatsio/util'
module Seatsio
module_function
class Chart
attr_reader :id, :key, :status, :name, :published_version_thumbnail_url,
:draft_version_thumbnail_url, :events, :tags, :archived,
:categories, :validation, :social_distancing_rulesets
def initialize(data)
@id = data['id']
@key = data['key']
@status = data['status']
@name = data['name']
@published_version_thumbnail_url = data['publishedVersionThumbnailUrl']
@draft_version_thumbnail_url = data['draftVersionThumbnailUrl']
@events = Event.create_list(data['events']) if data['events']
@tags = data['tags']
@archived = data['archived']
@validation = data['validation']
@social_distancing_rulesets = data['socialDistancingRulesets'].map {
|key, r| [key, SocialDistancingRuleset.new(r['name'],
number_of_disabled_seats_to_the_sides: r['numberOfDisabledSeatsToTheSides'],
disable_seats_in_front_and_behind: r['disableSeatsInFrontAndBehind'],
disable_diagonal_seats_in_front_and_behind: r['disableDiagonalSeatsInFrontAndBehind'],
number_of_disabled_aisle_seats: r['numberOfDisabledAisleSeats'],
max_group_size: r['maxGroupSize'],
max_occupancy_absolute: r['maxOccupancyAbsolute'],
max_occupancy_percentage: r['maxOccupancyPercentage'],
one_group_per_table: r['oneGroupPerTable'],
fixed_group_layout: r['fixedGroupLayout'],
disabled_seats: r['disabledSeats'],
enabled_seats: r['enabledSeats'],
index: r['index'])]
}.to_h
end
end
class ChartValidationResult
attr_reader :errors, :warnings
def initialize(data)
@errors = data['errors']
@warnings = data['warnings']
end
end
class ChartDraft < Chart
attr_reader :version
def initialize(data)
super(data)
@version = data['version']
end
end
class ForSaleConfig
attr_reader :for_sale, :objects, :categories
def initialize(data)
if data
@for_sale = data['forSale']
@objects = data['objects']
@categories = data['categories']
end
end
end
class TableBookingConfig
attr_reader :mode, :tables
def initialize(mode, tables = nil)
@mode = mode
@tables = tables
end
def self.inherit
TableBookingConfig.new('INHERIT')
end
def self.all_by_seat
TableBookingConfig.new('ALL_BY_SEAT')
end
def self.all_by_table
TableBookingConfig.new('ALL_BY_TABLE')
end
def self.custom(tables)
TableBookingConfig.new('CUSTOM', tables)
end
def self.from_json(data)
if data
TableBookingConfig.new(data['mode'], data['tables'])
end
end
end
class Channel
attr_reader :key, :name, :color, :index, :objects
def initialize(key, name, color, index, objects)
@key = key
@name = name
@color = color
@index = index
@objects = objects
end
def == (other)
self.key == other.key &&
self.name == other.name &&
self.color == other.color &&
self.index == other.index &&
self.objects == other.objects
end
end
class Event
attr_accessor :id, :key, :chart_key, :supports_best_available,
:table_booking_config, :for_sale_config, :created_on, :updated_on, :channels,
:social_distancing_ruleset_key
def initialize(data)
@id = data['id']
@key = data['key']
@chart_key = data['chartKey']
@supports_best_available = data['supportsBestAvailable']
@table_booking_config = TableBookingConfig::from_json(data['tableBookingConfig'])
@for_sale_config = ForSaleConfig.new(data['forSaleConfig']) if data['forSaleConfig']
@created_on = parse_date(data['createdOn'])
@updated_on = parse_date(data['updatedOn'])
@channels = data['channels'].map {
|d| Channel.new(d['key'], d['name'], d['color'], d['index'], d['objects'])
} if data['channels']
@social_distancing_ruleset_key = data['socialDistancingRulesetKey']
end
def self.create_list(list = [])
result = []
list.each do |item|
result << Event.new(item)
end
return result
end
end
class Events
attr_accessor :events
def initialize(data)
@events = Event.create_list(data['events']) if data['events']
end
end
class APIResponse
attr_reader :next_page_starts_after, :previous_page_ends_before, :items
def initialize(data)
@next_page_starts_after = data.fetch('next_page_starts_after', nil).to_i
@previous_page_ends_before = data.fetch('previous_page_ends_before', nil).to_i
@items = data.fetch('items', [])
end
end
class Subaccount
attr_reader :id, :secret_key, :designer_key, :public_key, :name, :active
def initialize(data)
@id = data['id']
@public_key = data['publicKey']
@secret_key = data['secretKey']
@designer_key = data['designerKey']
@name = data['name']
@active = data['active']
end
end
class Workspace
attr_reader :id, :name, :key, :secret_key, :is_test, :is_active, :is_default
def initialize(data)
@id = data['id']
@name = data['name']
@key = data['key']
@secret_key = data['secretKey']
@is_test = data['isTest']
@is_active = data['isActive']
@is_default = data['isDefault']
end
end
class ObjectStatus
FREE = 'free'
BOOKED = 'booked'
HELD = 'reservedByToken'
attr_reader :status, :hold_token, :order_id, :ticket_type,
:quantity, :extra_data, :for_sale
def initialize(data)
@status = data['status']
@hold_token = data['holdToken']
@order_id = data['orderId']
@ticket_type = data['ticketType']
@quantity = data['quantity']
@extra_data = data['extraData']
@for_sale = data['forSale']
end
end
class ChangeObjectStatusResult
attr_reader :objects
def initialize(data)
@objects = Seatsio.to_object_details(data['objects']);
end
end
class ChangeObjectStatusInBatchResult
attr_reader :results
def initialize(data)
@results = data['results'].map { |r| ChangeObjectStatusResult.new(r) }
end
end
class HoldToken
attr_reader :hold_token, :expires_at, :expires_in_seconds, :workspace_key
def initialize(data)
@hold_token = data['holdToken']
@expires_at = Time.parse(data['expiresAt'])
@expires_in_seconds = data['expiresInSeconds']
@workspace_key = data['workspaceKey']
end
end
class BestAvailableObjects
attr_reader :next_to_each_other, :objects, :object_details
def initialize(data)
@next_to_each_other = data['nextToEachOther']
@objects = data['objects']
@object_details = Seatsio.to_object_details(data['objectDetails'])
end
end
class ChartReportItem
attr_reader :label, :labels, :ids, :category_key, :category_label, :section, :entrance, :capacity, :object_type,
:left_neighbour, :right_neighbour, :book_as_a_whole, :distance_to_focal_point
def initialize(data)
@label = data['label']
@labels = data['labels']
@ids = data['ids']
@category_label = data['categoryLabel']
@category_key = data['categoryKey']
@section = data['section']
@entrance = data['entrance']
@capacity = data['capacity']
@object_type = data['objectType']
@left_neighbour = data['leftNeighbour']
@right_neighbour = data['rightNeighbour']
@book_as_a_whole = data['bookAsAWhole']
@distance_to_focal_point = data['distanceToFocalPoint']
end
end
class ChartReport
attr_reader :items
def initialize(data)
items = {}
data.each do |key, values|
items[key] = []
values.each do |value|
items[key] << ChartReportItem.new(value)
end
end
@items = items
end
end
class EventReport
attr_reader :items
def initialize(data)
if data.is_a? Array
items = []
data.each do |item|
items << EventReportItem.new(item)
end
@items = items
elsif data.nil?
@items = []
else
items = {}
data.each do |key, values|
items[key] = []
values.each do |value|
items[key] << EventReportItem.new(value)
end
end
@items = items
end
end
end
class EventReportItem
attr_reader :labels, :ids, :label, :order_id, :extra_data, :capacity, :status,
:category_key, :entrance, :object_type, :hold_token, :category_label,
:ticket_type, :num_booked, :num_free, :num_held, :for_sale, :section,
:is_accessible, :is_companion_seat, :has_restricted_view, :displayed_object_type,
:left_neighbour, :right_neighbour, :is_selectable, :is_disabled_by_social_distancing, :channel,
:book_as_a_whole, :distance_to_focal_point
def initialize(data)
@status = data['status']
@label = data['label']
@labels = data['labels']
@ids = data['ids']
@category_label = data['categoryLabel']
@category_key = data['categoryKey']
@ticket_type = data['ticketType']
@order_id = data['orderId']
@for_sale = data['forSale']
@hold_token = data['holdToken']
@section = data['section']
@entrance = data['entrance']
@num_booked = data['numBooked']
@num_free = data['numFree']
@num_held = data['numHeld']
@capacity = data['capacity']
@object_type = data['objectType']
@extra_data = data['extraData']
@is_accessible = data['isAccessible']
@is_companion_seat = data['isCompanionSeat']
@has_restricted_view = data['hasRestrictedView']
@displayed_object_type = data['displayedObjectType']
@left_neighbour = data['leftNeighbour']
@right_neighbour = data['rightNeighbour']
@is_selectable = data['isSelectable']
@is_disabled_by_social_distancing = data['isDisabledBySocialDistancing']
@channel = data['channel']
@book_as_a_whole = data['bookAsAWhole']
@distance_to_focal_point = data['distanceToFocalPoint']
end
end
class UsageSummaryForAllMoths
attr_reader :items
def initialize(data)
items = []
data.each do |item|
items << UsageSummaryForMonth.new(item)
end
@items = items
end
end
class UsageSummaryForMonth
def initialize(data)
@month = Month.from_json(data['month'])
@num_used_objects = data['numUsedObjects']
@num_first_bookings = data['numFirstBookings']
@num_first_bookings_by_status = data['numFirstBookingsByStatus']
@num_first_bookings_or_selections = data['numFirstBookingsOrSelections']
end
end
class UsageDetails
attr_reader :workspace, :usage_by_chart
def initialize(data)
@workspace = data['workspace']
@usage_by_chart = data['usageByChart'].map { |usage| UsageByChart.new(usage) }
end
end
class UsageByChart
attr_reader :chart, :usage_by_event
def initialize(data)
@chart = data['chart'] ? UsageChart.new(data['chart']) : nil
@usage_by_event = data['usageByEvent'].map { |usage| UsageByEvent.new(usage) }
end
end
class UsageChart
attr_reader :name, :key
def initialize(data)
@name = data['name']
@key = data['key']
end
end
class UsageByEvent
attr_reader :event, :num_used_objects, :num_first_bookings, :num_first_bookings_or_selections,
:num_ga_selections_without_booking, :num_non_ga_selections_without_booking, :num_object_selections
def initialize(data)
@event = UsageEvent.new(data['event'])
@num_used_objects = data['numUsedObjects']
@num_first_bookings = data['numFirstBookings']
@num_first_bookings_or_selections = data['numFirstBookingsOrSelections']
@num_ga_selections_without_booking = data['numGASelectionsWithoutBooking']
@num_non_ga_selections_without_booking = data['numNonGASelectionsWithoutBooking']
@num_object_selections = data['numObjectSelections']
end
end
class UsageEvent
attr_reader :id, :key
def initialize(data)
@id = data['id']
@key = data['key']
end
end
class UsageForObject
attr_reader :object, :num_first_bookings, :first_booking_date, :num_first_bookings, :num_first_bookings_or_selections
def initialize(data)
@object = data['object']
@num_first_bookings = data['numFirstBookings']
@first_booking_date = data['firstBookingDate'] ? DateTime.iso8601(data['firstBookingDate']) : nil
@num_first_selections = data['numFirstSelections']
@num_first_bookings_or_selections = data['numFirstBookingsOrSelections']
end
end
class Month
attr_reader :year, :month
def self.from_json(data)
@year = data['year']
@month = data['month']
self
end
def initialize(year, month)
@year = year
@month = month
end
def serialize
@year.to_s + "-" + @month.to_s.rjust(2, "0")
end
end
class StatusChange
attr_reader :extra_data, :object_label, :date, :id, :status, :event_id, :origin, :order_id, :quantity, :hold_token
def initialize(data)
@id = data['id']
@status = data['status']
@date = DateTime.iso8601(data['date'])
@object_label = data['objectLabel']
@event_id = data['eventId']
@extra_data = data['extraData']
@origin = StatusChangeOrigin.new(data['origin'])
@order_id = data['orderId']
@quantity = data['quantity']
@hold_token = data['holdToken']
end
end
class StatusChangeOrigin
attr_reader :type, :ip
def initialize(data)
@type = data['type']
@ip = data['ip']
end
end
def to_object_details(data)
object_details = {}
data.each do |key, value|
object_details[key] = EventReportItem.new(value)
end
object_details
end
class SocialDistancingRuleset
attr_reader :name, :number_of_disabled_seats_to_the_sides, :disable_seats_in_front_and_behind,
:disable_diagonal_seats_in_front_and_behind, :number_of_disabled_aisle_seats, :max_group_size, :max_occupancy_absolute,
:max_occupancy_percentage, :one_group_per_table, :fixed_group_layout, :disabled_seats, :enabled_seats, :index
def initialize(name, number_of_disabled_seats_to_the_sides: 0, disable_seats_in_front_and_behind: false, disable_diagonal_seats_in_front_and_behind: false,
number_of_disabled_aisle_seats: 0, max_group_size: 0, max_occupancy_absolute: 0, max_occupancy_percentage: 0, one_group_per_table: false,
fixed_group_layout: false, disabled_seats: [], enabled_seats: [], index: 0)
@name = name
@number_of_disabled_seats_to_the_sides = number_of_disabled_seats_to_the_sides
@disable_seats_in_front_and_behind = disable_seats_in_front_and_behind
@disable_diagonal_seats_in_front_and_behind = disable_diagonal_seats_in_front_and_behind
@number_of_disabled_aisle_seats = number_of_disabled_aisle_seats
@max_group_size = max_group_size
@max_occupancy_absolute = max_occupancy_absolute
@max_occupancy_percentage = max_occupancy_percentage
@one_group_per_table = one_group_per_table
@fixed_group_layout = fixed_group_layout
@disabled_seats = disabled_seats
@enabled_seats = enabled_seats
@index = index
end
def self.fixed(name, disabled_seats: [], index: 0)
return SocialDistancingRuleset.new(name, index: index, disabled_seats: disabled_seats, fixed_group_layout: true)
end
def self.rule_based(name, number_of_disabled_seats_to_the_sides: 0, disable_seats_in_front_and_behind: false, disable_diagonal_seats_in_front_and_behind: false,
number_of_disabled_aisle_seats: 0, max_group_size: 0, max_occupancy_absolute: 0, max_occupancy_percentage: 0, one_group_per_table: false,
disabled_seats: [], enabled_seats: [], index: 0)
return SocialDistancingRuleset.new(name,
number_of_disabled_seats_to_the_sides: number_of_disabled_seats_to_the_sides,
disable_seats_in_front_and_behind: disable_seats_in_front_and_behind,
disable_diagonal_seats_in_front_and_behind: disable_diagonal_seats_in_front_and_behind,
number_of_disabled_aisle_seats: number_of_disabled_aisle_seats,
max_group_size: max_group_size,
max_occupancy_absolute: max_occupancy_absolute,
max_occupancy_percentage: max_occupancy_percentage,
one_group_per_table: one_group_per_table,
fixed_group_layout: false,
disabled_seats: disabled_seats,
enabled_seats: enabled_seats,
index: index)
end
def == (other)
self.name == other.name &&
self.number_of_disabled_seats_to_the_sides == other.number_of_disabled_seats_to_the_sides &&
self.disable_seats_in_front_and_behind == other.disable_seats_in_front_and_behind &&
self.disable_diagonal_seats_in_front_and_behind == other.disable_diagonal_seats_in_front_and_behind &&
self.number_of_disabled_aisle_seats == other.number_of_disabled_aisle_seats &&
self.max_group_size == other.max_group_size &&
self.max_occupancy_absolute == other.max_occupancy_absolute &&
self.max_occupancy_percentage == other.max_occupancy_percentage &&
self.one_group_per_table == other.one_group_per_table &&
self.fixed_group_layout == other.fixed_group_layout &&
self.disabled_seats == other.disabled_seats &&
self.enabled_seats == other.enabled_seats &&
self.index == other.index
end
end
end