basketball 0.0.8 → 0.0.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +9 -19
- data/CHANGELOG.md +1 -39
- data/README.md +75 -93
- data/basketball.gemspec +3 -6
- data/exe/{basketball-season-scheduling → basketball-coordinator} +1 -1
- data/exe/{basketball-draft → basketball-room} +1 -1
- data/lib/basketball/app/coordinator_cli.rb +250 -0
- data/lib/basketball/app/coordinator_repository.rb +114 -0
- data/lib/basketball/app/document_repository.rb +67 -0
- data/lib/basketball/app/file_store.rb +38 -0
- data/lib/basketball/app/in_memory_store.rb +42 -0
- data/lib/basketball/app/league_repository.rb +20 -0
- data/lib/basketball/app/league_serializable.rb +54 -0
- data/lib/basketball/{draft/cli.rb → app/room_cli.rb} +74 -80
- data/lib/basketball/app/room_repository.rb +149 -0
- data/lib/basketball/app.rb +20 -0
- data/lib/basketball/draft/assessment.rb +31 -0
- data/lib/basketball/draft/event.rb +3 -2
- data/lib/basketball/draft/front_office.rb +35 -28
- data/lib/basketball/draft/{pick_event.rb → pick.rb} +13 -6
- data/lib/basketball/draft/room.rb +119 -119
- data/lib/basketball/draft/{player_search.rb → scout.rb} +4 -9
- data/lib/basketball/draft/skip.rb +12 -0
- data/lib/basketball/draft.rb +13 -6
- data/lib/basketball/entity.rb +19 -10
- data/lib/basketball/org/league.rb +68 -0
- data/lib/basketball/org/player.rb +26 -0
- data/lib/basketball/{draft → org}/position.rb +3 -2
- data/lib/basketball/org/team.rb +38 -0
- data/lib/basketball/org.rb +12 -0
- data/lib/basketball/season/arena.rb +113 -0
- data/lib/basketball/season/calendar.rb +41 -72
- data/lib/basketball/season/coordinator.rb +186 -128
- data/lib/basketball/season/{preseason_game.rb → exhibition.rb} +2 -1
- data/lib/basketball/season/game.rb +15 -10
- data/lib/basketball/season/matchup.rb +27 -0
- data/lib/basketball/season/opponent.rb +15 -0
- data/lib/basketball/season/{season_game.rb → regular.rb} +2 -1
- data/lib/basketball/season/result.rb +37 -0
- data/lib/basketball/season.rb +12 -13
- data/lib/basketball/value_object.rb +8 -27
- data/lib/basketball/value_object_dsl.rb +30 -0
- data/lib/basketball/version.rb +1 -1
- data/lib/basketball.rb +9 -4
- metadata +37 -44
- data/lib/basketball/draft/league.rb +0 -70
- data/lib/basketball/draft/player.rb +0 -43
- data/lib/basketball/draft/room_serializer.rb +0 -186
- data/lib/basketball/draft/roster.rb +0 -37
- data/lib/basketball/draft/sim_event.rb +0 -23
- data/lib/basketball/draft/skip_event.rb +0 -13
- data/lib/basketball/season/calendar_serializer.rb +0 -94
- data/lib/basketball/season/conference.rb +0 -57
- data/lib/basketball/season/division.rb +0 -43
- data/lib/basketball/season/league.rb +0 -114
- data/lib/basketball/season/league_serializer.rb +0 -99
- data/lib/basketball/season/scheduling_cli.rb +0 -198
- data/lib/basketball/season/team.rb +0 -21
@@ -1,186 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require_relative 'front_office'
|
4
|
-
require_relative 'player'
|
5
|
-
require_relative 'pick_event'
|
6
|
-
require_relative 'sim_event'
|
7
|
-
require_relative 'skip_event'
|
8
|
-
|
9
|
-
module Basketball
|
10
|
-
module Draft
|
11
|
-
class RoomSerializer
|
12
|
-
EVENT_CLASSES = {
|
13
|
-
'PickEvent' => PickEvent,
|
14
|
-
'SimEvent' => SimEvent,
|
15
|
-
'SkipEvent' => SkipEvent
|
16
|
-
}.freeze
|
17
|
-
|
18
|
-
private_constant :EVENT_CLASSES
|
19
|
-
|
20
|
-
def to_hash(room)
|
21
|
-
{
|
22
|
-
'info' => serialize_info(room),
|
23
|
-
'room' => serialize_room(room),
|
24
|
-
'league' => serialize_league(room)
|
25
|
-
}
|
26
|
-
end
|
27
|
-
|
28
|
-
def from_hash(json)
|
29
|
-
front_offices = deserialize_front_offices(json)
|
30
|
-
players = deserialize_players(json)
|
31
|
-
events = deserialize_events(json, players, front_offices)
|
32
|
-
|
33
|
-
room_opts = {
|
34
|
-
players:,
|
35
|
-
front_offices:,
|
36
|
-
events:
|
37
|
-
}
|
38
|
-
|
39
|
-
room_opts[:rounds] = json.dig('room', 'rounds') if json.dig('room', 'rounds')
|
40
|
-
|
41
|
-
Room.new(**room_opts)
|
42
|
-
end
|
43
|
-
|
44
|
-
def deserialize(string)
|
45
|
-
json = JSON.parse(string)
|
46
|
-
|
47
|
-
from_hash(json)
|
48
|
-
end
|
49
|
-
|
50
|
-
def serialize(room)
|
51
|
-
to_hash(room).to_json
|
52
|
-
end
|
53
|
-
|
54
|
-
private
|
55
|
-
|
56
|
-
def serialize_room(room)
|
57
|
-
{
|
58
|
-
'rounds' => room.rounds,
|
59
|
-
'front_offices' => serialize_front_offices(room),
|
60
|
-
'players' => serialize_players(room),
|
61
|
-
'events' => serialize_events(room.events)
|
62
|
-
}
|
63
|
-
end
|
64
|
-
|
65
|
-
def serialize_info(room)
|
66
|
-
{
|
67
|
-
'total_picks' => room.total_picks,
|
68
|
-
'current_round' => room.current_round,
|
69
|
-
'current_round_pick' => room.current_round_pick,
|
70
|
-
'current_front_office' => room.current_front_office&.id,
|
71
|
-
'current_pick' => room.current_pick,
|
72
|
-
'remaining_picks' => room.remaining_picks,
|
73
|
-
'done' => room.done?
|
74
|
-
}
|
75
|
-
end
|
76
|
-
|
77
|
-
def serialize_league(room)
|
78
|
-
league = room.to_league
|
79
|
-
|
80
|
-
rosters = league.rosters.to_h do |roster|
|
81
|
-
[
|
82
|
-
roster.id,
|
83
|
-
{
|
84
|
-
'players' => roster.players.map(&:id)
|
85
|
-
}
|
86
|
-
]
|
87
|
-
end
|
88
|
-
|
89
|
-
{
|
90
|
-
'free_agents' => league.free_agents.map(&:id),
|
91
|
-
'rosters' => rosters
|
92
|
-
}
|
93
|
-
end
|
94
|
-
|
95
|
-
def serialize_front_offices(room)
|
96
|
-
room.front_offices.to_h do |front_office|
|
97
|
-
[
|
98
|
-
front_office.id,
|
99
|
-
{
|
100
|
-
'name' => front_office.name,
|
101
|
-
'fuzz' => front_office.fuzz,
|
102
|
-
'depth' => front_office.depth,
|
103
|
-
'prioritized_positions' => front_office.prioritized_positions.map(&:code)
|
104
|
-
}
|
105
|
-
]
|
106
|
-
end
|
107
|
-
end
|
108
|
-
|
109
|
-
def serialize_players(room)
|
110
|
-
room.players.to_h do |player|
|
111
|
-
[
|
112
|
-
player.id,
|
113
|
-
{
|
114
|
-
'first_name' => player.first_name,
|
115
|
-
'last_name' => player.last_name,
|
116
|
-
'overall' => player.overall,
|
117
|
-
'position' => player.position.code
|
118
|
-
}
|
119
|
-
]
|
120
|
-
end
|
121
|
-
end
|
122
|
-
|
123
|
-
def serialize_events(events)
|
124
|
-
events.map do |event|
|
125
|
-
{
|
126
|
-
'type' => event.class.name.split('::').last,
|
127
|
-
'front_office' => event.front_office.id,
|
128
|
-
'pick' => event.pick,
|
129
|
-
'round' => event.round,
|
130
|
-
'round_pick' => event.round_pick
|
131
|
-
}.tap do |hash|
|
132
|
-
hash['player'] = event.player.id if event.respond_to?(:player)
|
133
|
-
end
|
134
|
-
end
|
135
|
-
end
|
136
|
-
|
137
|
-
def deserialize_front_offices(json)
|
138
|
-
(json.dig('room', 'front_offices') || []).map do |id, front_office_hash|
|
139
|
-
prioritized_positions = (front_office_hash['prioritized_positions'] || []).map do |v|
|
140
|
-
Position.new(v)
|
141
|
-
end
|
142
|
-
|
143
|
-
front_office_opts = {
|
144
|
-
id:,
|
145
|
-
name: front_office_hash['name'],
|
146
|
-
prioritized_positions:,
|
147
|
-
fuzz: front_office_hash['fuzz'],
|
148
|
-
depth: front_office_hash['depth']
|
149
|
-
}
|
150
|
-
|
151
|
-
FrontOffice.new(**front_office_opts)
|
152
|
-
end
|
153
|
-
end
|
154
|
-
|
155
|
-
def deserialize_players(json)
|
156
|
-
(json.dig('room', 'players') || []).map do |id, player_hash|
|
157
|
-
player_opts = {
|
158
|
-
id:,
|
159
|
-
first_name: player_hash['first_name'],
|
160
|
-
last_name: player_hash['last_name'],
|
161
|
-
overall: player_hash['overall'],
|
162
|
-
position: Position.new(player_hash['position'])
|
163
|
-
}
|
164
|
-
|
165
|
-
Player.new(**player_opts)
|
166
|
-
end
|
167
|
-
end
|
168
|
-
|
169
|
-
def deserialize_events(json, players, front_offices)
|
170
|
-
(json.dig('room', 'events') || []).map do |event_hash|
|
171
|
-
event_opts = event_hash.slice('pick', 'round', 'round_pick').merge(
|
172
|
-
front_office: front_offices.find { |t| t.id == event_hash['front_office'] }
|
173
|
-
)
|
174
|
-
|
175
|
-
class_constant = EVENT_CLASSES.fetch(event_hash['type'])
|
176
|
-
|
177
|
-
if [PickEvent, SimEvent].include?(class_constant)
|
178
|
-
event_opts[:player] = players.find { |p| p.id == event_hash['player'] }
|
179
|
-
end
|
180
|
-
|
181
|
-
class_constant.new(**event_opts)
|
182
|
-
end
|
183
|
-
end
|
184
|
-
end
|
185
|
-
end
|
186
|
-
end
|
@@ -1,37 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Draft
|
5
|
-
class Roster < Entity
|
6
|
-
class PlayerRequiredError < StandardError; end
|
7
|
-
|
8
|
-
attr_reader :name, :players
|
9
|
-
|
10
|
-
def initialize(id:, name: '', players: [])
|
11
|
-
super(id)
|
12
|
-
|
13
|
-
@name = name.to_s
|
14
|
-
@players = players.each { |p| register!(p) }
|
15
|
-
|
16
|
-
freeze
|
17
|
-
end
|
18
|
-
|
19
|
-
def registered?(player)
|
20
|
-
players.include?(player)
|
21
|
-
end
|
22
|
-
|
23
|
-
def sign!(player)
|
24
|
-
raise PlayerRequiredError, 'player is required' unless player
|
25
|
-
raise PlayerAlreadyRegisteredError, "#{player} already registered for #{id}" if registered?(player)
|
26
|
-
|
27
|
-
players << player
|
28
|
-
|
29
|
-
self
|
30
|
-
end
|
31
|
-
|
32
|
-
def to_s
|
33
|
-
(["[#{super}] #{name} Roster"] + players.map(&:to_s)).join("\n")
|
34
|
-
end
|
35
|
-
end
|
36
|
-
end
|
37
|
-
end
|
@@ -1,23 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Draft
|
5
|
-
class SimEvent < Event
|
6
|
-
attr_reader_value :player
|
7
|
-
|
8
|
-
def initialize(front_office:, player:, pick:, round:, round_pick:)
|
9
|
-
super(front_office:, pick:, round:, round_pick:)
|
10
|
-
|
11
|
-
raise ArgumentError, 'player required' unless player
|
12
|
-
|
13
|
-
@player = player
|
14
|
-
|
15
|
-
freeze
|
16
|
-
end
|
17
|
-
|
18
|
-
def to_s
|
19
|
-
"#{player} auto-picked #{super}"
|
20
|
-
end
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
@@ -1,94 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require_relative 'game'
|
4
|
-
require_relative 'preseason_game'
|
5
|
-
require_relative 'season_game'
|
6
|
-
|
7
|
-
module Basketball
|
8
|
-
module Season
|
9
|
-
class CalendarSerializer
|
10
|
-
GAME_CLASSES = {
|
11
|
-
'PreseasonGame' => PreseasonGame,
|
12
|
-
'SeasonGame' => SeasonGame
|
13
|
-
}.freeze
|
14
|
-
|
15
|
-
def to_hash(calendar)
|
16
|
-
teams = calendar.games.flat_map(&:teams).uniq
|
17
|
-
|
18
|
-
{
|
19
|
-
'year' => calendar.preseason_start_date.year,
|
20
|
-
'teams' => serialize_teams(teams),
|
21
|
-
'games' => serialize_games(calendar.games)
|
22
|
-
}
|
23
|
-
end
|
24
|
-
|
25
|
-
def from_hash(json)
|
26
|
-
Calendar.new(
|
27
|
-
year: json['year'].to_i,
|
28
|
-
games: deserialize_games(json)
|
29
|
-
)
|
30
|
-
end
|
31
|
-
|
32
|
-
def deserialize(string)
|
33
|
-
json = JSON.parse(string)
|
34
|
-
|
35
|
-
from_hash(json)
|
36
|
-
end
|
37
|
-
|
38
|
-
def serialize(calendar)
|
39
|
-
to_hash(calendar).to_json
|
40
|
-
end
|
41
|
-
|
42
|
-
private
|
43
|
-
|
44
|
-
## Deserialization
|
45
|
-
|
46
|
-
def deserialize_games(json)
|
47
|
-
teams = deserialize_teams(json['teams'])
|
48
|
-
|
49
|
-
(json['games'] || []).map do |game_hash|
|
50
|
-
GAME_CLASSES.fetch(game_hash['type']).new(
|
51
|
-
date: Date.parse(game_hash['date']),
|
52
|
-
home_team: teams.fetch(game_hash['home_team']),
|
53
|
-
away_team: teams.fetch(game_hash['away_team'])
|
54
|
-
)
|
55
|
-
end
|
56
|
-
end
|
57
|
-
|
58
|
-
def deserialize_teams(teams)
|
59
|
-
(teams || []).to_h do |id, team_hash|
|
60
|
-
team = Team.new(id:, name: team_hash['name'])
|
61
|
-
|
62
|
-
[
|
63
|
-
team.id,
|
64
|
-
team
|
65
|
-
]
|
66
|
-
end
|
67
|
-
end
|
68
|
-
|
69
|
-
## Serialization
|
70
|
-
|
71
|
-
def serialize_teams(teams)
|
72
|
-
teams.to_h do |team|
|
73
|
-
[
|
74
|
-
team.id,
|
75
|
-
{
|
76
|
-
'name' => team.name
|
77
|
-
}
|
78
|
-
]
|
79
|
-
end
|
80
|
-
end
|
81
|
-
|
82
|
-
def serialize_games(games)
|
83
|
-
games.sort_by(&:date).map do |game|
|
84
|
-
{
|
85
|
-
'type' => game.class.name.split('::').last,
|
86
|
-
'date' => game.date.to_s,
|
87
|
-
'home_team' => game.home_team.id,
|
88
|
-
'away_team' => game.away_team.id
|
89
|
-
}
|
90
|
-
end
|
91
|
-
end
|
92
|
-
end
|
93
|
-
end
|
94
|
-
end
|
@@ -1,57 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Season
|
5
|
-
class Conference < Entity
|
6
|
-
DIVISIONS_SIZE = 3
|
7
|
-
|
8
|
-
attr_reader :name, :divisions
|
9
|
-
|
10
|
-
def initialize(id:, name: '', divisions: [])
|
11
|
-
super(id)
|
12
|
-
|
13
|
-
@name = name.to_s
|
14
|
-
@divisions = []
|
15
|
-
|
16
|
-
divisions.each { |d| register_division!(d) }
|
17
|
-
|
18
|
-
if divisions.length != DIVISIONS_SIZE
|
19
|
-
raise BadDivisionsSizeError, "#{id} should have exactly #{DIVISIONS_SIZE} divisions"
|
20
|
-
end
|
21
|
-
|
22
|
-
freeze
|
23
|
-
end
|
24
|
-
|
25
|
-
def to_s
|
26
|
-
(["[#{super}] #{name}"] + divisions.map(&:to_s)).join("\n")
|
27
|
-
end
|
28
|
-
|
29
|
-
def division?(division)
|
30
|
-
divisions.include?(division)
|
31
|
-
end
|
32
|
-
|
33
|
-
def teams
|
34
|
-
divisions.flat_map(&:teams)
|
35
|
-
end
|
36
|
-
|
37
|
-
def team?(team)
|
38
|
-
teams.include?(team)
|
39
|
-
end
|
40
|
-
|
41
|
-
private
|
42
|
-
|
43
|
-
def register_division!(division)
|
44
|
-
raise ArgumentError, 'division is required' unless division
|
45
|
-
raise DivisionAlreadyRegisteredError, "#{division} already registered" if division?(division)
|
46
|
-
|
47
|
-
division.teams.each do |team|
|
48
|
-
raise TeamAlreadyRegisteredError, "#{team} already registered" if team?(team)
|
49
|
-
end
|
50
|
-
|
51
|
-
divisions << division
|
52
|
-
|
53
|
-
self
|
54
|
-
end
|
55
|
-
end
|
56
|
-
end
|
57
|
-
end
|
@@ -1,43 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Season
|
5
|
-
class Division < Entity
|
6
|
-
TEAMS_SIZE = 5
|
7
|
-
|
8
|
-
attr_reader :name, :teams
|
9
|
-
|
10
|
-
def initialize(id:, name: '', teams: [])
|
11
|
-
super(id)
|
12
|
-
|
13
|
-
@name = name.to_s
|
14
|
-
@teams = []
|
15
|
-
|
16
|
-
teams.each { |t| register_team!(t) }
|
17
|
-
|
18
|
-
raise BadTeamsSizeError, "#{id} should have exactly #{TEAMS_SIZE} teams" if teams.length != TEAMS_SIZE
|
19
|
-
|
20
|
-
freeze
|
21
|
-
end
|
22
|
-
|
23
|
-
def to_s
|
24
|
-
(["[#{super}] #{name}"] + teams.map(&:to_s)).join("\n")
|
25
|
-
end
|
26
|
-
|
27
|
-
def team?(team)
|
28
|
-
teams.include?(team)
|
29
|
-
end
|
30
|
-
|
31
|
-
private
|
32
|
-
|
33
|
-
def register_team!(team)
|
34
|
-
raise ArgumentError, 'team is required' unless team
|
35
|
-
raise TeamAlreadyRegisteredError, "#{team} already registered" if team?(team)
|
36
|
-
|
37
|
-
teams << team
|
38
|
-
|
39
|
-
self
|
40
|
-
end
|
41
|
-
end
|
42
|
-
end
|
43
|
-
end
|
@@ -1,114 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Season
|
5
|
-
class League
|
6
|
-
class UnknownTeamError < StandardError; end
|
7
|
-
|
8
|
-
class << self
|
9
|
-
def generate_random; end
|
10
|
-
end
|
11
|
-
|
12
|
-
CONFERENCES_SIZE = 2
|
13
|
-
|
14
|
-
attr_reader :conferences
|
15
|
-
|
16
|
-
def initialize(conferences: [])
|
17
|
-
@conferences = []
|
18
|
-
|
19
|
-
conferences.each { |c| register_conference!(c) }
|
20
|
-
|
21
|
-
if conferences.length != CONFERENCES_SIZE
|
22
|
-
raise BadConferencesSizeError, "there has to be #{CONFERENCES_SIZE} conferences"
|
23
|
-
end
|
24
|
-
|
25
|
-
freeze
|
26
|
-
end
|
27
|
-
|
28
|
-
def to_s
|
29
|
-
(['League'] + conferences.map(&:to_s)).join("\n")
|
30
|
-
end
|
31
|
-
|
32
|
-
def divisions
|
33
|
-
conferences.flat_map(&:divisions)
|
34
|
-
end
|
35
|
-
|
36
|
-
def conference?(conference)
|
37
|
-
conferences.include?(conference)
|
38
|
-
end
|
39
|
-
|
40
|
-
def division?(division)
|
41
|
-
divisions.include?(division)
|
42
|
-
end
|
43
|
-
|
44
|
-
def team?(team)
|
45
|
-
teams.include?(team)
|
46
|
-
end
|
47
|
-
|
48
|
-
def teams
|
49
|
-
conferences.flat_map do |conference|
|
50
|
-
conference.divisions.flat_map(&:teams)
|
51
|
-
end
|
52
|
-
end
|
53
|
-
|
54
|
-
def conference_for(team)
|
55
|
-
conferences.find { |c| c.divisions.find { |d| d.teams.include?(team) } }
|
56
|
-
end
|
57
|
-
|
58
|
-
def division_for(team)
|
59
|
-
conference_for(team)&.divisions&.find { |d| d.teams.include?(team) }
|
60
|
-
end
|
61
|
-
|
62
|
-
# Same conference, same division
|
63
|
-
def division_opponents_for(team)
|
64
|
-
division = division_for(team)
|
65
|
-
|
66
|
-
return nil unless division
|
67
|
-
|
68
|
-
division.teams - [team]
|
69
|
-
end
|
70
|
-
|
71
|
-
# Same conference, different division
|
72
|
-
def cross_division_opponents_for(team)
|
73
|
-
conference = conference_for(team)
|
74
|
-
division = division_for(team)
|
75
|
-
|
76
|
-
return nil unless conference && division
|
77
|
-
|
78
|
-
other_divisions = conference.divisions - [division]
|
79
|
-
|
80
|
-
other_divisions.flat_map(&:teams)
|
81
|
-
end
|
82
|
-
|
83
|
-
# Different conference
|
84
|
-
def cross_conference_opponents_for(team)
|
85
|
-
conference = conference_for(team)
|
86
|
-
|
87
|
-
return nil unless conference
|
88
|
-
|
89
|
-
other_conferences = conferences - [conference]
|
90
|
-
|
91
|
-
other_conferences.flat_map { |c| c.divisions.flat_map(&:teams) }
|
92
|
-
end
|
93
|
-
|
94
|
-
private
|
95
|
-
|
96
|
-
def register_conference!(conference)
|
97
|
-
raise ArgumentError, 'conference is required' unless conference
|
98
|
-
raise ConferenceAlreadyRegisteredError, "#{conference} already registered" if conference?(conference)
|
99
|
-
|
100
|
-
conference.divisions.each do |division|
|
101
|
-
raise DivisionAlreadyRegisteredError, "#{division} already registered" if division?(division)
|
102
|
-
|
103
|
-
division.teams.each do |team|
|
104
|
-
raise TeamAlreadyRegisteredError, "#{team} already registered" if team?(team)
|
105
|
-
end
|
106
|
-
end
|
107
|
-
|
108
|
-
conferences << conference
|
109
|
-
|
110
|
-
self
|
111
|
-
end
|
112
|
-
end
|
113
|
-
end
|
114
|
-
end
|
@@ -1,99 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module Basketball
|
4
|
-
module Season
|
5
|
-
class LeagueSerializer
|
6
|
-
def to_hash(league)
|
7
|
-
{
|
8
|
-
'conferences' => serialize_conferences(league.conferences)
|
9
|
-
}
|
10
|
-
end
|
11
|
-
|
12
|
-
def from_hash(json)
|
13
|
-
conferences = deserialize_conferences(json['conferences'])
|
14
|
-
|
15
|
-
League.new(conferences:)
|
16
|
-
end
|
17
|
-
|
18
|
-
def deserialize(string)
|
19
|
-
json = JSON.parse(string)
|
20
|
-
|
21
|
-
from_hash(json)
|
22
|
-
end
|
23
|
-
|
24
|
-
def serialize(league)
|
25
|
-
to_hash(league).to_json
|
26
|
-
end
|
27
|
-
|
28
|
-
private
|
29
|
-
|
30
|
-
## Deserialization
|
31
|
-
|
32
|
-
def deserialize_conferences(conferences)
|
33
|
-
(conferences || []).map do |conference_id, conference_hash|
|
34
|
-
Conference.new(
|
35
|
-
id: conference_id,
|
36
|
-
name: conference_hash['name'],
|
37
|
-
divisions: deserialize_divisions(conference_hash['divisions'])
|
38
|
-
)
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
def deserialize_divisions(divisions)
|
43
|
-
(divisions || []).map do |division_id, division_hash|
|
44
|
-
Division.new(
|
45
|
-
id: division_id,
|
46
|
-
name: division_hash['name'],
|
47
|
-
teams: deserialize_teams(division_hash['teams'])
|
48
|
-
)
|
49
|
-
end
|
50
|
-
end
|
51
|
-
|
52
|
-
def deserialize_teams(teams)
|
53
|
-
(teams || []).map do |team_id, team_hash|
|
54
|
-
Team.new(
|
55
|
-
id: team_id,
|
56
|
-
name: team_hash['name']
|
57
|
-
)
|
58
|
-
end
|
59
|
-
end
|
60
|
-
|
61
|
-
## Serialization
|
62
|
-
|
63
|
-
def serialize_conferences(conferences)
|
64
|
-
conferences.to_h do |conference|
|
65
|
-
[
|
66
|
-
conference.id,
|
67
|
-
{
|
68
|
-
'name' => conference.name,
|
69
|
-
'divisions' => serialize_divisions(conference.divisions)
|
70
|
-
}
|
71
|
-
]
|
72
|
-
end
|
73
|
-
end
|
74
|
-
|
75
|
-
def serialize_divisions(divisions)
|
76
|
-
divisions.to_h do |division|
|
77
|
-
[
|
78
|
-
division.id,
|
79
|
-
{
|
80
|
-
'name' => division.name,
|
81
|
-
'teams' => serialize_teams(division.teams)
|
82
|
-
}
|
83
|
-
]
|
84
|
-
end
|
85
|
-
end
|
86
|
-
|
87
|
-
def serialize_teams(teams)
|
88
|
-
teams.to_h do |team|
|
89
|
-
[
|
90
|
-
team.id,
|
91
|
-
{
|
92
|
-
'name' => team.name
|
93
|
-
}
|
94
|
-
]
|
95
|
-
end
|
96
|
-
end
|
97
|
-
end
|
98
|
-
end
|
99
|
-
end
|