tf2_line_parser 0.6.5 → 0.7.0
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/Gemfile.lock +1 -1
- data/lib/tf2_line_parser/events/carry_object.rb +11 -0
- data/lib/tf2_line_parser/events/disconnect.rb +1 -1
- data/lib/tf2_line_parser/events/drop_object.rb +11 -0
- data/lib/tf2_line_parser/events/event.rb +1 -1
- data/lib/tf2_line_parser/events/game_paused.rb +11 -0
- data/lib/tf2_line_parser/events/game_unpaused.rb +11 -0
- data/lib/tf2_line_parser/events/intermission_win_limit.rb +1 -1
- data/lib/tf2_line_parser/events/killed_object.rb +5 -4
- data/lib/tf2_line_parser/events/loading_map.rb +22 -0
- data/lib/tf2_line_parser/events/log_file_closed.rb +19 -0
- data/lib/tf2_line_parser/events/log_file_started.rb +24 -0
- data/lib/tf2_line_parser/events/map_started.rb +23 -0
- data/lib/tf2_line_parser/events/match_pause.rb +22 -0
- data/lib/tf2_line_parser/events/match_unpause.rb +22 -0
- data/lib/tf2_line_parser/events/meta_data.rb +23 -0
- data/lib/tf2_line_parser/events/name_change.rb +25 -0
- data/lib/tf2_line_parser/events/object_detonated.rb +11 -0
- data/lib/tf2_line_parser/events/object_event.rb +24 -0
- data/lib/tf2_line_parser/events/pause_length.rb +19 -0
- data/lib/tf2_line_parser/events/round_overtime.rb +11 -0
- data/lib/tf2_line_parser/events/server_cvar.rb +23 -0
- data/lib/tf2_line_parser/events/steam_userid_validated.rb +22 -0
- data/lib/tf2_line_parser/line.rb +18 -1
- data/lib/tf2_line_parser/version.rb +1 -1
- data/lib/tf2_line_parser.rb +1 -0
- data/spec/lib/tf2_line_parser/parser_spec.rb +176 -3
- metadata +20 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: c9ae1ffbaaa2ebff7e8cf30040ef166b57c12285cb2870f397f968c8daf9a883
|
|
4
|
+
data.tar.gz: 9245015c50d5de623077004a90cd79c45c406094a082220ac1282ecee1fc0ca6
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 8eb08df2bf3d064ed0bb24cc63ab5e0f78f12b6d59ed019f6f3fabb698e562a906d799d64f643462781a33122ebfab2971686beb2e4bf08a30b6fe59fa8305eb
|
|
7
|
+
data.tar.gz: c359b30e53b652a2a889692199e6adb44821c4e0368d8793ce6773dffaca13e9aee58026f7e1d1bc1e72675fd9bd47d79f6a4a1ae185f60660ebcdde6551ada3
|
data/Gemfile.lock
CHANGED
|
@@ -14,7 +14,7 @@ module TF2LineParser
|
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
def self.regex
|
|
17
|
-
@regex ||= /#{regex_time} #{regex_player} disconnected \(reason
|
|
17
|
+
@regex ||= /#{regex_time} #{regex_player} disconnected \(reason "(?'message'.*?)(?:"\)\s*$|$)/.freeze
|
|
18
18
|
end
|
|
19
19
|
end
|
|
20
20
|
end
|
|
@@ -48,7 +48,7 @@ module TF2LineParser
|
|
|
48
48
|
@types ||= [ShotFired, ShotHit, PositionReport, HeadshotDamage, Airshot, Damage, AirshotHeal, Heal, PickupItem, Assist, Kill, CaptureBlock, PointCapture, ChargeDeployed,
|
|
49
49
|
MedicDeath, MedicDeathEx, EmptyUber, ChargeReady, ChargeEnded, FirstHealAfterSpawn, LostUberAdvantage, BuiltObject, PlayerExtinguished, JoinedTeam, EnteredGame, RoleChange, Spawn, Suicide, KilledObject, Say, TeamSay, Domination, Revenge, RoundWin, CurrentScore,
|
|
50
50
|
RoundLength, RoundStart, RoundSetupBegin, RoundSetupEnd, MiniRoundStart, MiniRoundSelected, MiniRoundLength, MiniRoundWin, WorldIntermissionWinLimit, IntermissionWinLimit, Connect, Disconnect, RconCommand, ConsoleSay, MatchEnd, FinalScore,
|
|
51
|
-
RoundStalemate, Unknown].freeze
|
|
51
|
+
RoundStalemate, ServerCvar, CarryObject, DropObject, ObjectDetonated, SteamUseridValidated, LogFileStarted, LogFileClosed, LoadingMap, MapStarted, MetaData, RoundOvertime, GamePaused, GameUnpaused, PauseLength, MatchPause, MatchUnpause, NameChange, Unknown].freeze
|
|
52
52
|
end
|
|
53
53
|
|
|
54
54
|
def self.regex_results(matched_line)
|
|
@@ -4,7 +4,7 @@ module TF2LineParser
|
|
|
4
4
|
attr_reader :time, :team, :reason
|
|
5
5
|
|
|
6
6
|
def self.regex
|
|
7
|
-
@regex ||= /#{regex_time} Team "(?'team'Red|Blue|RED|BLUE)" triggered "Intermission_Win_Limit" due to (?'reason'.*)
|
|
7
|
+
@regex ||= /#{regex_time} Team "(?'team'Red|Blue|RED|BLUE)" triggered "Intermission_Win_Limit"(?: due to (?'reason'.*))?/.freeze
|
|
8
8
|
end
|
|
9
9
|
|
|
10
10
|
def self.attributes
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
module TF2LineParser
|
|
2
2
|
module Events
|
|
3
3
|
class KilledObject < Event
|
|
4
|
-
attr_reader :time, :player, :object, :weapon, :objectowner
|
|
4
|
+
attr_reader :time, :player, :object, :weapon, :objectowner, :assist
|
|
5
5
|
|
|
6
6
|
def self.regex
|
|
7
7
|
@regex ||= /#{regex_time} #{regex_player} triggered "killedobject" #{regex_object_info}#{regex_attacker_position}?/.freeze
|
|
8
8
|
end
|
|
9
9
|
|
|
10
10
|
def self.regex_object_info
|
|
11
|
-
@regex_object_info ||= '\(object "(?\'object\'[^"]+)"\) \(weapon "(?\'weapon\'[^"]+)"\) \(objectowner "(?\'objectowner_section\'.*?)"\)'
|
|
11
|
+
@regex_object_info ||= '\(object "(?\'object\'[^"]+)"\)(?: \(weapon "(?\'weapon\'[^"]+)"\))? \(objectowner "(?\'objectowner_section\'.*?)"\)(?: \(assist "(?\'assist\'\d+)"\))?'
|
|
12
12
|
end
|
|
13
13
|
|
|
14
14
|
def self.regex_attacker_position
|
|
@@ -16,7 +16,7 @@ module TF2LineParser
|
|
|
16
16
|
end
|
|
17
17
|
|
|
18
18
|
def self.attributes
|
|
19
|
-
@attributes ||= %i[time player_section object weapon objectowner_section]
|
|
19
|
+
@attributes ||= %i[time player_section object weapon objectowner_section assist]
|
|
20
20
|
end
|
|
21
21
|
|
|
22
22
|
def self.regex_results(matched_line)
|
|
@@ -42,12 +42,13 @@ module TF2LineParser
|
|
|
42
42
|
out
|
|
43
43
|
end
|
|
44
44
|
|
|
45
|
-
def initialize(time, player_name, player_uid, player_steam_id, player_team, object, weapon, objectowner_name, objectowner_uid, objectowner_steam_id, objectowner_team)
|
|
45
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team, object, weapon, objectowner_name, objectowner_uid, objectowner_steam_id, objectowner_team, assist = nil)
|
|
46
46
|
@time = parse_time(time)
|
|
47
47
|
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
48
48
|
@object = object
|
|
49
49
|
@weapon = weapon
|
|
50
50
|
@objectowner = Player.new(objectowner_name, objectowner_uid, objectowner_steam_id, objectowner_team)
|
|
51
|
+
@assist = assist == '1'
|
|
51
52
|
end
|
|
52
53
|
end
|
|
53
54
|
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class LoadingMap < Event
|
|
6
|
+
attr_reader :time, :map
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} Loading map "(?'map'[^"]*)"/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time map]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, map)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@map = map
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class LogFileClosed < Event
|
|
6
|
+
def self.regex
|
|
7
|
+
@regex ||= /#{regex_time} Log file closed\.?\s*$/.freeze
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def self.attributes
|
|
11
|
+
@attributes ||= [:time]
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def initialize(time)
|
|
15
|
+
@time = parse_time(time)
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
end
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class LogFileStarted < Event
|
|
6
|
+
attr_reader :time, :file, :game, :version
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} Log file started \(file "(?'file'[^"]*)"\) \(game "(?'game'[^"]*)"\) \(version "(?'version'[^"]*)"\)/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time file game version]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, file, game, version)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@file = file
|
|
19
|
+
@game = game
|
|
20
|
+
@version = version
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class MapStarted < Event
|
|
6
|
+
attr_reader :time, :map, :crc
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} Started map "(?'map'[^"]*)" \(CRC "(?'crc'[^"]*)"\)/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time map crc]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, map, crc)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@map = map
|
|
19
|
+
@crc = crc
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class MatchPause < Event
|
|
6
|
+
attr_reader :time, :player
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} #{regex_player} triggered "matchpause"/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time player_section]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class MatchUnpause < Event
|
|
6
|
+
attr_reader :time, :player
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} #{regex_player} triggered "matchunpause"/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time player_section]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class MetaData < Event
|
|
6
|
+
attr_reader :time, :key, :value
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} World triggered "meta_data" \((?'key'\w+) "(?'value'.*)"\)/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time key value]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, key, value)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@key = key
|
|
19
|
+
@value = value
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class NameChange < Event
|
|
6
|
+
attr_reader :time, :player, :new_name
|
|
7
|
+
|
|
8
|
+
# The old name must end in a <uid><steamid><team> tag, so a name that merely
|
|
9
|
+
# contains ' changed name to ' can't make another line look like a name change.
|
|
10
|
+
def self.regex
|
|
11
|
+
@regex ||= /#{regex_time} "(?<player_section>.*?<\d+><[^<>"]*><[^<>"]*>)" changed name to "(?'new_name'.*)"/.freeze
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def self.attributes
|
|
15
|
+
@attributes ||= %i[time player_section new_name]
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team, new_name)
|
|
19
|
+
@time = parse_time(time)
|
|
20
|
+
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
21
|
+
@new_name = new_name
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class ObjectEvent < Event
|
|
6
|
+
attr_reader :time, :player, :object, :position
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} #{regex_player} triggered "#{keyword}" \(object "(?'object'[^"]+)"\)(?: \(position "(?'position'[^"]+)"\))?/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time player_section object position]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team, object, position)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
19
|
+
@object = object
|
|
20
|
+
@position = position
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class PauseLength < RoundEventWithVariables
|
|
6
|
+
def self.round_type
|
|
7
|
+
@round_type ||= 'Pause_Length'
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
def self.round_variable_regex
|
|
11
|
+
@round_variable_regex ||= /\(seconds "(?'length'.*)"\)/.freeze
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def self.round_variable
|
|
15
|
+
@round_variable ||= :length
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class ServerCvar < Event
|
|
6
|
+
attr_reader :time, :name, :value
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} server_cvar: "(?'name'[^"]*)" "(?'value'.*)"/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time name value]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, name, value)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@name = name
|
|
19
|
+
@value = value
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module TF2LineParser
|
|
4
|
+
module Events
|
|
5
|
+
class SteamUseridValidated < Event
|
|
6
|
+
attr_reader :time, :player
|
|
7
|
+
|
|
8
|
+
def self.regex
|
|
9
|
+
@regex ||= /#{regex_time} #{regex_player} STEAM USERID validated\s*$/.freeze
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.attributes
|
|
13
|
+
@attributes ||= %i[time player_section]
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def initialize(time, player_name, player_uid, player_steam_id, player_team)
|
|
17
|
+
@time = parse_time(time)
|
|
18
|
+
@player = Player.new(player_name, player_uid, player_steam_id, player_team)
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
data/lib/tf2_line_parser/line.rb
CHANGED
|
@@ -28,6 +28,9 @@ module TF2LineParser
|
|
|
28
28
|
'lost_uber_advantage' => [Events::LostUberAdvantage],
|
|
29
29
|
'builtobject' => [Events::BuiltObject],
|
|
30
30
|
'player_builtobject' => [Events::BuiltObject],
|
|
31
|
+
'player_carryobject' => [Events::CarryObject],
|
|
32
|
+
'player_dropobject' => [Events::DropObject],
|
|
33
|
+
'object_detonated' => [Events::ObjectDetonated],
|
|
31
34
|
'player_extinguished' => [Events::PlayerExtinguished],
|
|
32
35
|
'joined team' => [Events::JoinedTeam],
|
|
33
36
|
'entered the game' => [Events::EnteredGame],
|
|
@@ -46,6 +49,13 @@ module TF2LineParser
|
|
|
46
49
|
'Mini_Round_Length' => [Events::MiniRoundLength],
|
|
47
50
|
'Mini_Round_Win' => [Events::MiniRoundWin],
|
|
48
51
|
'Intermission_Win_Limit' => [Events::WorldIntermissionWinLimit, Events::IntermissionWinLimit],
|
|
52
|
+
'meta_data' => [Events::MetaData],
|
|
53
|
+
'Round_Overtime' => [Events::RoundOvertime],
|
|
54
|
+
'Game_Paused' => [Events::GamePaused],
|
|
55
|
+
'Game_Unpaused' => [Events::GameUnpaused],
|
|
56
|
+
'Pause_Length' => [Events::PauseLength],
|
|
57
|
+
'matchpause' => [Events::MatchPause],
|
|
58
|
+
'matchunpause' => [Events::MatchUnpause],
|
|
49
59
|
'Round_Stalemate' => [Events::RoundStalemate],
|
|
50
60
|
'Game_Over' => [Events::MatchEnd],
|
|
51
61
|
'connected, address' => [Events::Connect],
|
|
@@ -62,7 +72,14 @@ module TF2LineParser
|
|
|
62
72
|
Events::JoinedTeam, Events::EnteredGame, Events::RoleChange,
|
|
63
73
|
Events::Spawn, Events::Suicide, Events::Connect, Events::Disconnect,
|
|
64
74
|
Events::CurrentScore, Events::FinalScore, Events::RconCommand,
|
|
65
|
-
Events::ConsoleSay, Events::
|
|
75
|
+
Events::ConsoleSay, Events::ServerCvar,
|
|
76
|
+
Events::SteamUseridValidated,
|
|
77
|
+
Events::LogFileStarted,
|
|
78
|
+
Events::LogFileClosed,
|
|
79
|
+
Events::LoadingMap,
|
|
80
|
+
Events::MapStarted,
|
|
81
|
+
Events::NameChange,
|
|
82
|
+
Events::Unknown
|
|
66
83
|
].freeze
|
|
67
84
|
|
|
68
85
|
CHAT_REGEX = /#{Events::Event.regex_time} #{Events::Event.regex_chat_player} (?<chat_type>say|say_team) "/
|
data/lib/tf2_line_parser.rb
CHANGED
|
@@ -14,6 +14,7 @@ require 'tf2_line_parser/events/score'
|
|
|
14
14
|
require 'tf2_line_parser/events/role_change'
|
|
15
15
|
require 'tf2_line_parser/events/damage'
|
|
16
16
|
require 'tf2_line_parser/events/heal'
|
|
17
|
+
require 'tf2_line_parser/events/object_event'
|
|
17
18
|
Dir["#{File.dirname(__FILE__)}/tf2_line_parser/events/*.rb"].sort.each { |file| require file }
|
|
18
19
|
require 'tf2_line_parser/line'
|
|
19
20
|
|
|
@@ -757,7 +757,7 @@ module TF2LineParser
|
|
|
757
757
|
objectowner_uid = '24'
|
|
758
758
|
objectowner_steam_id = '[U:1:161147993]'
|
|
759
759
|
objectowner_team = 'Blue'
|
|
760
|
-
expect(Events::KilledObject).to receive(:new).with(anything, player_name, player_uid, player_steam_id, player_team, object, weapon, objectowner_name, objectowner_uid, objectowner_steam_id, objectowner_team)
|
|
760
|
+
expect(Events::KilledObject).to receive(:new).with(anything, player_name, player_uid, player_steam_id, player_team, object, weapon, objectowner_name, objectowner_uid, objectowner_steam_id, objectowner_team, nil)
|
|
761
761
|
parse(line)
|
|
762
762
|
end
|
|
763
763
|
|
|
@@ -779,10 +779,183 @@ module TF2LineParser
|
|
|
779
779
|
parse(line)
|
|
780
780
|
end
|
|
781
781
|
|
|
782
|
+
it 'recognizes assisted killed object' do
|
|
783
|
+
result = parse('L 06/15/2026 - 19:56:47: "Jib<3><[U:1:111]><Red>" triggered "killedobject" (object "OBJ_SENTRYGUN") (objectowner "Owner<22><[U:1:222]><Blue>") (assist "1") (assister_position "-2268 2938 -255") (attacker_position "-2263 2869 -255")')
|
|
784
|
+
expect(result).to be_a(Events::KilledObject)
|
|
785
|
+
expect(result.player.name).to eq('Jib')
|
|
786
|
+
expect(result.object).to eq('OBJ_SENTRYGUN')
|
|
787
|
+
expect(result.objectowner.steam_id).to eq('[U:1:222]')
|
|
788
|
+
expect(result.weapon).to be_nil
|
|
789
|
+
expect(result.assist).to be(true)
|
|
790
|
+
end
|
|
791
|
+
|
|
792
|
+
it 'does not mark killed object by the killer as assisted' do
|
|
793
|
+
result = parse('L 06/15/2026 - 19:56:47: "Jib<3><[U:1:111]><Red>" triggered "killedobject" (object "OBJ_SENTRYGUN") (weapon "tf_projectile_rocket") (objectowner "Owner<22><[U:1:222]><Blue>") (attacker_position "0 0 0")')
|
|
794
|
+
expect(result.weapon).to eq('tf_projectile_rocket')
|
|
795
|
+
expect(result.assist).to be(false)
|
|
796
|
+
end
|
|
797
|
+
|
|
798
|
+
it 'recognizes team intermission win limit without a reason' do
|
|
799
|
+
result = parse('L 06/15/2026 - 22:07:11: Team "RED" triggered "Intermission_Win_Limit"')
|
|
800
|
+
expect(result).to be_a(Events::IntermissionWinLimit)
|
|
801
|
+
expect(result.team).to eq('RED')
|
|
802
|
+
expect(result.reason).to be_nil
|
|
803
|
+
end
|
|
804
|
+
|
|
805
|
+
it 'recognizes disconnects whose reason continues on the next line' do
|
|
806
|
+
result = parse('L 06/15/2026 - 19:05:27: "Jib<3><[U:1:111]><Red>" disconnected (reason "Client left game (Steam auth ticket has been canceled)' + "\n")
|
|
807
|
+
expect(result).to be_a(Events::Disconnect)
|
|
808
|
+
expect(result.player.name).to eq('Jib')
|
|
809
|
+
expect(result.message).to eq('Client left game (Steam auth ticket has been canceled)')
|
|
810
|
+
end
|
|
811
|
+
|
|
812
|
+
it 'keeps quotes inside a complete disconnect reason' do
|
|
813
|
+
result = parse('L 06/15/2026 - 19:05:27: "Jib<3><[U:1:111]><Red>" disconnected (reason "Kicked "x") by admin")' + "\n")
|
|
814
|
+
expect(result.message).to eq('Kicked "x") by admin')
|
|
815
|
+
end
|
|
816
|
+
|
|
817
|
+
it 'recognizes server cvar changes' do
|
|
818
|
+
result = parse('L 02/22/2026 - 13:42:46: server_cvar: "mp_timelimit" "30"')
|
|
819
|
+
expect(result).to be_a(Events::ServerCvar)
|
|
820
|
+
expect(result.name).to eq('mp_timelimit')
|
|
821
|
+
expect(result.value).to eq('30')
|
|
822
|
+
end
|
|
823
|
+
|
|
824
|
+
it 'recognizes server cvar changes with an empty value' do
|
|
825
|
+
expect(parse('L 02/22/2026 - 13:42:46: server_cvar: "sv_contact" ""').value).to eq('')
|
|
826
|
+
end
|
|
827
|
+
|
|
828
|
+
it 'recognizes picking up a building' do
|
|
829
|
+
result = parse('L 06/15/2026 - 21:53:08: "Jib<3><[U:1:111]><Red>" triggered "player_carryobject" (object "OBJ_SENTRYGUN") (position "-804 663 544")')
|
|
830
|
+
expect(result).to be_a(Events::CarryObject)
|
|
831
|
+
expect(result.player.name).to eq('Jib')
|
|
832
|
+
expect(result.object).to eq('OBJ_SENTRYGUN')
|
|
833
|
+
expect(result.position).to eq('-804 663 544')
|
|
834
|
+
end
|
|
835
|
+
|
|
836
|
+
it 'recognizes dropping a carried building' do
|
|
837
|
+
result = parse('L 06/15/2026 - 21:53:08: "Jib<3><[U:1:111]><Red>" triggered "player_dropobject" (object "OBJ_SENTRYGUN") (position "-804 663 544")')
|
|
838
|
+
expect(result).to be_a(Events::DropObject)
|
|
839
|
+
expect(result.player.name).to eq('Jib')
|
|
840
|
+
expect(result.object).to eq('OBJ_SENTRYGUN')
|
|
841
|
+
expect(result.position).to eq('-804 663 544')
|
|
842
|
+
end
|
|
843
|
+
|
|
844
|
+
it 'recognizes detonating a building' do
|
|
845
|
+
result = parse('L 06/15/2026 - 21:53:08: "Jib<3><[U:1:111]><Red>" triggered "object_detonated" (object "OBJ_SENTRYGUN") (position "-804 663 544")')
|
|
846
|
+
expect(result).to be_a(Events::ObjectDetonated)
|
|
847
|
+
expect(result.player.name).to eq('Jib')
|
|
848
|
+
expect(result.object).to eq('OBJ_SENTRYGUN')
|
|
849
|
+
expect(result.position).to eq('-804 663 544')
|
|
850
|
+
end
|
|
851
|
+
|
|
852
|
+
it 'recognizes steam userid validation' do
|
|
853
|
+
result = parse('L 02/02/2014 - 22:10:19: "A "fake" name<21><[U:1:111]><>" STEAM USERID validated')
|
|
854
|
+
expect(result).to be_a(Events::SteamUseridValidated)
|
|
855
|
+
expect(result.player.name).to eq('A "fake" name')
|
|
856
|
+
expect(result.player.steam_id).to eq('[U:1:111]')
|
|
857
|
+
end
|
|
858
|
+
|
|
859
|
+
it 'recognizes log file started' do
|
|
860
|
+
result = parse('L 02/07/2013 - 21:21:08: Log file started (file "logs/L0207006.log") (game "/home/tf2/tf") (version "5198")')
|
|
861
|
+
expect(result).to be_a(Events::LogFileStarted)
|
|
862
|
+
expect(result.file).to eq('logs/L0207006.log')
|
|
863
|
+
expect(result.game).to eq('/home/tf2/tf')
|
|
864
|
+
expect(result.version).to eq('5198')
|
|
865
|
+
end
|
|
866
|
+
|
|
867
|
+
it 'recognizes log file closed' do
|
|
868
|
+
expect(parse('L 02/22/2026 - 13:42:56: Log file closed.')).to be_a(Events::LogFileClosed)
|
|
869
|
+
end
|
|
870
|
+
|
|
871
|
+
it 'recognizes log file closed without a trailing period' do
|
|
872
|
+
expect(parse('L 02/07/2013 - 21:56:13: Log file closed')).to be_a(Events::LogFileClosed)
|
|
873
|
+
end
|
|
874
|
+
|
|
875
|
+
it 'recognizes loading map' do
|
|
876
|
+
result = parse('L 06/15/2026 - 21:32:52: Loading map "cp_process_f12"')
|
|
877
|
+
expect(result).to be_a(Events::LoadingMap)
|
|
878
|
+
expect(result.map).to eq('cp_process_f12')
|
|
879
|
+
end
|
|
880
|
+
|
|
881
|
+
it 'recognizes started map' do
|
|
882
|
+
result = parse('L 06/15/2026 - 21:32:52: Started map "cp_process_f12" (CRC "df0d50ef")')
|
|
883
|
+
expect(result).to be_a(Events::MapStarted)
|
|
884
|
+
expect(result.map).to eq('cp_process_f12')
|
|
885
|
+
expect(result.crc).to eq('df0d50ef')
|
|
886
|
+
end
|
|
887
|
+
|
|
888
|
+
it 'does not report started map as an unknown event' do
|
|
889
|
+
result = parse('L 06/15/2026 - 21:32:52: Started map "cp_process_f12" (CRC "df0d50ef")')
|
|
890
|
+
expect(result).not_to be_a(Events::Unknown)
|
|
891
|
+
end
|
|
892
|
+
|
|
893
|
+
it 'does not parse chat mentioning a started map as a map start' do
|
|
894
|
+
expect(parse('L 06/15/2026 - 21:32:52: "Jib<3><[U:1:111]><Red>" say "Started map "cp_reset" (CRC "abc")"')).to be_a(Events::Say)
|
|
895
|
+
end
|
|
896
|
+
|
|
897
|
+
it 'recognizes meta data' do
|
|
898
|
+
result = parse('L 06/15/2026 - 21:55:48: World triggered "meta_data" (map "cp_process_f12")')
|
|
899
|
+
expect(result).to be_a(Events::MetaData)
|
|
900
|
+
expect(result.key).to eq('map')
|
|
901
|
+
expect(result.value).to eq('cp_process_f12')
|
|
902
|
+
end
|
|
903
|
+
|
|
904
|
+
it 'recognizes meta data with quotes in the value' do
|
|
905
|
+
result = parse('L 06/15/2026 - 21:55:48: World triggered "meta_data" (title "BLU vs "RED"")')
|
|
906
|
+
expect(result).to be_a(Events::MetaData)
|
|
907
|
+
expect(result.key).to eq('title')
|
|
908
|
+
expect(result.value).to eq('BLU vs "RED"')
|
|
909
|
+
end
|
|
910
|
+
|
|
911
|
+
it 'recognizes round overtime' do
|
|
912
|
+
expect(parse('L 06/15/2026 - 19:33:13: World triggered "Round_Overtime"')).to be_a(Events::RoundOvertime)
|
|
913
|
+
end
|
|
914
|
+
|
|
915
|
+
it 'recognizes game paused' do
|
|
916
|
+
expect(parse('L 06/15/2026 - 19:33:13: World triggered "Game_Paused"')).to be_a(Events::GamePaused)
|
|
917
|
+
end
|
|
918
|
+
|
|
919
|
+
it 'recognizes game unpaused' do
|
|
920
|
+
expect(parse('L 06/15/2026 - 19:33:13: World triggered "Game_Unpaused"')).to be_a(Events::GameUnpaused)
|
|
921
|
+
end
|
|
922
|
+
|
|
923
|
+
it 'recognizes pause length' do
|
|
924
|
+
result = parse('L 06/15/2026 - 19:33:22: World triggered "Pause_Length" (seconds "8.69")')
|
|
925
|
+
expect(result).to be_a(Events::PauseLength)
|
|
926
|
+
expect(result.length).to eq('8.69')
|
|
927
|
+
end
|
|
928
|
+
|
|
929
|
+
it 'recognizes a player pausing the match' do
|
|
930
|
+
result = parse('L 06/15/2026 - 19:33:13: "Jib<3><[U:1:111]><Red>" triggered "matchpause"')
|
|
931
|
+
expect(result).to be_a(Events::MatchPause)
|
|
932
|
+
expect(result.player.steam_id).to eq('[U:1:111]')
|
|
933
|
+
end
|
|
934
|
+
|
|
935
|
+
it 'recognizes a player unpausing the match' do
|
|
936
|
+
result = parse('L 06/15/2026 - 19:33:13: "Jib<3><[U:1:111]><Red>" triggered "matchunpause"')
|
|
937
|
+
expect(result).to be_a(Events::MatchUnpause)
|
|
938
|
+
expect(result.player.steam_id).to eq('[U:1:111]')
|
|
939
|
+
end
|
|
940
|
+
|
|
941
|
+
it 'recognizes name changes' do
|
|
942
|
+
result = parse('L 02/07/2013 - 21:22:10: "Jib<3><[U:1:111]><Red>" changed name to "New "quoted" name"')
|
|
943
|
+
expect(result).to be_a(Events::NameChange)
|
|
944
|
+
expect(result.player.name).to eq('Jib')
|
|
945
|
+
expect(result.player.steam_id).to eq('[U:1:111]')
|
|
946
|
+
expect(result.new_name).to eq('New "quoted" name')
|
|
947
|
+
end
|
|
948
|
+
|
|
949
|
+
it 'does not treat a player whose name contains changed name to as a name change' do
|
|
950
|
+
result = parse('L 02/07/2013 - 21:22:10: "x" changed name to "y<3><[U:1:111]><Red>" STEAM USERID validated')
|
|
951
|
+
expect(result).to be_a(Events::SteamUseridValidated)
|
|
952
|
+
expect(result.player.steam_id).to eq('[U:1:111]')
|
|
953
|
+
end
|
|
954
|
+
|
|
782
955
|
it 'deals with unknown lines' do
|
|
783
|
-
line =
|
|
956
|
+
line = 'L 02/07/2013 - 21:21:08: VAC secure mode is activated.'
|
|
784
957
|
time = '02/07/2013 - 21:21:08'
|
|
785
|
-
unknown = '
|
|
958
|
+
unknown = 'VAC secure mode is activated.'
|
|
786
959
|
expect(Events::Unknown).to receive(:new).with(time, unknown)
|
|
787
960
|
parse(line)
|
|
788
961
|
end
|
metadata
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: tf2_line_parser
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.7.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Arie
|
|
8
8
|
bindir: bin
|
|
9
9
|
cert_chain: []
|
|
10
|
-
date: 2026-
|
|
10
|
+
date: 2026-11-01 00:00:00.000000000 Z
|
|
11
11
|
dependencies:
|
|
12
12
|
- !ruby/object:Gem::Dependency
|
|
13
13
|
name: coveralls_reborn
|
|
@@ -85,6 +85,7 @@ files:
|
|
|
85
85
|
- lib/tf2_line_parser/events/assist.rb
|
|
86
86
|
- lib/tf2_line_parser/events/built_object.rb
|
|
87
87
|
- lib/tf2_line_parser/events/capture_block.rb
|
|
88
|
+
- lib/tf2_line_parser/events/carry_object.rb
|
|
88
89
|
- lib/tf2_line_parser/events/charge_deployed.rb
|
|
89
90
|
- lib/tf2_line_parser/events/charge_ended.rb
|
|
90
91
|
- lib/tf2_line_parser/events/charge_ready.rb
|
|
@@ -95,26 +96,40 @@ files:
|
|
|
95
96
|
- lib/tf2_line_parser/events/damage.rb
|
|
96
97
|
- lib/tf2_line_parser/events/disconnect.rb
|
|
97
98
|
- lib/tf2_line_parser/events/domination.rb
|
|
99
|
+
- lib/tf2_line_parser/events/drop_object.rb
|
|
98
100
|
- lib/tf2_line_parser/events/empty_uber.rb
|
|
99
101
|
- lib/tf2_line_parser/events/entered_game.rb
|
|
100
102
|
- lib/tf2_line_parser/events/event.rb
|
|
101
103
|
- lib/tf2_line_parser/events/feign_death.rb
|
|
102
104
|
- lib/tf2_line_parser/events/final_score.rb
|
|
103
105
|
- lib/tf2_line_parser/events/first_heal_after_spawn.rb
|
|
106
|
+
- lib/tf2_line_parser/events/game_paused.rb
|
|
107
|
+
- lib/tf2_line_parser/events/game_unpaused.rb
|
|
104
108
|
- lib/tf2_line_parser/events/headshot_damage.rb
|
|
105
109
|
- lib/tf2_line_parser/events/heal.rb
|
|
106
110
|
- lib/tf2_line_parser/events/intermission_win_limit.rb
|
|
107
111
|
- lib/tf2_line_parser/events/joined_team.rb
|
|
108
112
|
- lib/tf2_line_parser/events/kill.rb
|
|
109
113
|
- lib/tf2_line_parser/events/killed_object.rb
|
|
114
|
+
- lib/tf2_line_parser/events/loading_map.rb
|
|
115
|
+
- lib/tf2_line_parser/events/log_file_closed.rb
|
|
116
|
+
- lib/tf2_line_parser/events/log_file_started.rb
|
|
110
117
|
- lib/tf2_line_parser/events/lost_uber_advantage.rb
|
|
118
|
+
- lib/tf2_line_parser/events/map_started.rb
|
|
111
119
|
- lib/tf2_line_parser/events/match_end.rb
|
|
120
|
+
- lib/tf2_line_parser/events/match_pause.rb
|
|
121
|
+
- lib/tf2_line_parser/events/match_unpause.rb
|
|
112
122
|
- lib/tf2_line_parser/events/medic_death.rb
|
|
113
123
|
- lib/tf2_line_parser/events/medic_death_ex.rb
|
|
124
|
+
- lib/tf2_line_parser/events/meta_data.rb
|
|
114
125
|
- lib/tf2_line_parser/events/mini_round_length.rb
|
|
115
126
|
- lib/tf2_line_parser/events/mini_round_selected.rb
|
|
116
127
|
- lib/tf2_line_parser/events/mini_round_start.rb
|
|
117
128
|
- lib/tf2_line_parser/events/mini_round_win.rb
|
|
129
|
+
- lib/tf2_line_parser/events/name_change.rb
|
|
130
|
+
- lib/tf2_line_parser/events/object_detonated.rb
|
|
131
|
+
- lib/tf2_line_parser/events/object_event.rb
|
|
132
|
+
- lib/tf2_line_parser/events/pause_length.rb
|
|
118
133
|
- lib/tf2_line_parser/events/pickup_item.rb
|
|
119
134
|
- lib/tf2_line_parser/events/player_action_event.rb
|
|
120
135
|
- lib/tf2_line_parser/events/player_extinguished.rb
|
|
@@ -127,15 +142,18 @@ files:
|
|
|
127
142
|
- lib/tf2_line_parser/events/round_event_with_variables.rb
|
|
128
143
|
- lib/tf2_line_parser/events/round_event_without_variables.rb
|
|
129
144
|
- lib/tf2_line_parser/events/round_length.rb
|
|
145
|
+
- lib/tf2_line_parser/events/round_overtime.rb
|
|
130
146
|
- lib/tf2_line_parser/events/round_setup_begin.rb
|
|
131
147
|
- lib/tf2_line_parser/events/round_setup_end.rb
|
|
132
148
|
- lib/tf2_line_parser/events/round_stalemate.rb
|
|
133
149
|
- lib/tf2_line_parser/events/round_start.rb
|
|
134
150
|
- lib/tf2_line_parser/events/round_win.rb
|
|
135
151
|
- lib/tf2_line_parser/events/score.rb
|
|
152
|
+
- lib/tf2_line_parser/events/server_cvar.rb
|
|
136
153
|
- lib/tf2_line_parser/events/shot_fired.rb
|
|
137
154
|
- lib/tf2_line_parser/events/shot_hit.rb
|
|
138
155
|
- lib/tf2_line_parser/events/spawn.rb
|
|
156
|
+
- lib/tf2_line_parser/events/steam_userid_validated.rb
|
|
139
157
|
- lib/tf2_line_parser/events/suicide.rb
|
|
140
158
|
- lib/tf2_line_parser/events/unknown.rb
|
|
141
159
|
- lib/tf2_line_parser/events/world_intermission_win_limit.rb
|