How to parse HL log data

From Scriptwiki
Jump to: navigation, search
; HL Log Listener snippet by NaNg
; Date: 11-06-2011
; Tested on mIRC 7.19
;
; HL Log window for HL log based engines (HL1, Source etc.),
; Based on the HL Log Standard found at http://developer.valvesoftware.com/wiki/HL_Log_Standard
;
; ==================== NOTE! ====================
; This does NOT query the server to start logging, this should be done on your end, by sending
; this command to the server:
;   logaddress_add <listening_ip> <listening_port>
; <listening_port> should be the same in this command as well as in the /hllog command.
;
; This snippet was built based on CS (1.6) logs, therefore only two team colors exist (besides default).
; You can easly add more team colors by adding them to the $hllog.teamcolor alias found here.
;
; Usage:
; * /hllog <ip> <port> <listening_port>

alias hllog {
  ; Validate arguments (simple, no need for full validation).
  if ((!$longip($1)) || ($2 !isnum 1-65536) || ($3 !isnum 1-65536)) {
    echo -ag hllog: Invalid parameters.
    return
  }

  ; Save the server's address.
  var %server.addr = $+($1,:,$2)

  ; Check that the user has not opened a HL log window for the same server already.
  ; This makes sure that the user won't have a log step over another log for the same server.
  if ($window(%server.addr)) {
    echo -ag HL log window for %server.addr is already open! close it before trying.
    return
  }

  ; Open the HL log window whilst activating it, hide the @ prefix and maximize it.
  window -ak0x @ $+ %server.addr
  aline 12 @ $+ %server.addr HL log window, now listening to: %server.addr

  ; Set the socket name we'll use.
  var %sockname = $+($hllog.prefix, %server.addr)

  ; Start listening to HL logs from the server.
  sockudp -k %sockname $3 $1 $2
}

; Parses the given player.
alias hlplayer {
  if (!$regex($1-, /"(.*?)<([^>]*)><([^>]*)><([^>]*)>"/)) {
    echo -ag hlpalyer: Invalid parameters.
    return
  }

  if ($prop == name) { return $regml(1) }
  elseif ($prop == id) { return $regml(2) }
  elseif ($prop == authid) { return $regml(3) }
  elseif ($prop == team) { return $regml(4) }

  return $true
}

; Gets the given property's value.
alias -l hllog.prop {
  ; Number of keys is requested.
  if ($$2 == 0) {
    return $regex($1, /\((\S+)(?: "([^"]*)"|())\)/g)
  }

  if ($regex($1, /\(( $+ $2 $+ )(?: "([^"]*)"|())\)/i)) {
    return $iif($regml(2) == $null, $true, $ifmatch)
  }

  return $null
}

; Get the team's corresponding color.
alias -l hllog.teamcolor {
  if ($1 == CT) { return 12 }
  elseif ($1 == TERRORIST) { return 04 }

  ; Default color if team is not recognized.
  return 14
}

alias -l hllog.prefix { return hllog }

; If the user has closed the HL log window, clear the socket.
on *:CLOSE:@: {
  ; If there's a socket named accordingly, close it.
  if ($sock($+($hllog.prefix, $remove($target, @)))) {
    sockclose $+($hllog.prefix, $remove($target, @))
  }
}

on *:UDPREAD:$($+($hllog.prefix, *)): {
  ; Get the window name for the current game server.
  var %hllog.window = $+(@, $remove($sockname, $hllog.prefix))

  ; If there were errors, $sockerr will tell us so.
  ; Write the error message to the window and clear the connection.
  if ($sockerr) {
    aline 04 %hllog.window * Error: Reading from socket: $sock($sockname).wsmsg
    sockclose $sockname
    return
  }

  sockread -f %hllog.value

  ; Separate the server log time and the log line itself.
  noop $regex(%hllog.value, /L ((?:0[1-9]|1[0-2])/(?:0[1-9]|[12][0-9]|3[01])/[0-9]{4} - (?:[01][0-9]|2[0-3]):[0-5][0-9]:[0-5][0-9]): (.*)[\n\r\0]*$/)

  ; Invalid log line.
  if ($regml(0) == 0) { return }

  ; Get the server log time (usually un-needed. if you do need it - uncomment the next line).
  ; var %hllog.time = $regml(1)
  var %hllog.cmd = $regml(2)

  ; If the command is a comment, disregard it.
  if (//* iswm %hllog.cmd) { return }

  ; Server cvar change (event 001b).
  elseif (server cvar* iswm %hllog.cmd) {
    noop $regex(%hllog.cmd, /^Server cvar "([^"]+)" = "([^"]+)"(.*)$/i)

    ; If the line was succesfully parsed.
    if ($regml(0) > 0) {
      var %cvar.name = $regml(1)
      var %cvar.value = $regml(2)
      ; var %hllog.props = $regml(3)

      aline 3 %hllog.window Cvar " $+ %cvar.name $+ " has been changed, new value: " $+ %cvar.value $+ "
    }
  }

  ; Rcon (events 004a and 004b).
  elseif ((Bad Rcon:* iswm %hllog.cmd) || (Rcon:* iswm %hllog.cmd)) {
    noop $regex(%hllog.cmd, /^((?:Bad )?)Rcon: "[^"]+ ([^"]+) "([^"]+)" (.*)" [^"\x28]+ "([^"]+:[^"]+)"(.*)$/i)

    ; Parse the event's details.
    var %hllog.badrcon = $iif($regml(1) == $null, $false, $true)
    ; var %hllog.challenge = $regml(2)
    ; var %hllog.rconpwd = $regml(3)
    var %hllog.rconcmd = $regml(4)
    var %hllog.sender = $regml(5)
    ; var %hllog.props = $regml(6)

    aline 4 %hllog.window $iif(%hllog.badrcon, Bad) RCON: %hllog.rconcmd (from: %hllog.sender $+ )
  }

  ; Player got kicked (event 052b).
  elseif (Kick:* iswm %hllog.cmd) {
    noop $regex(%hllog.cmd, /^Kick: ("[^"]+") ([^"]+) "([^"]+)"(.*)$/i)

    ; Parse the event's details.
    var %hllog.player = $regml(1)
    ; var %hllog.noun = $regml(2)
    var %hllog.kicker = $regml(3)
    var %hllog.props = $regml(4)

    aline 4 %hllog.window $+($chr(3), $hllog.teamcolor($hlplayer(%hllog.player).team), $hlplayer(%hllog.player).name, $chr(15)) was kicked by %hllog.kicker with reason: $+(", $hllog.prop(%hllog.props, message), ")
  }

  ; Team score report (event 065).
  elseif ($regex(%hllog.cmd, /^Team "([^"]+)" ([^"\x28]+) "([^"]+)" ([^"\x28]+) "([^"]+)"(.*)$/i)) {
    var %hllog.team = $regml(1)
    var %hllog.score = $regml(3)
    var %hllog.numPlayers = $regml(5)
    var %hllog.props = $regml(7)

    aline 3 %hllog.window Team $+($chr(3), $hllog.teamcolor(%hllog.team), %hllog.team, $chr(15)) scored %hllog.score with %hllog.numPlayers players %hllog.props
  }

  ; Player score report (event 067).
  elseif ($regex(%hllog.cmd, /^Player ("[^"]+") ([^"\x28]+) "([^"]+)"(.*)$/i)) {
    var %hllog.player = $regml(1)
    var %hllog.score = $regml(3)
    var %hllog.props = $regml(4)

    aline 3 %hllog.window Player $+($chr(3), $hllog.teamcolor($hlplayer(%hllog.player).team), $hlplayer(%hllog.player).name, $chr(15)) scored %hllog.score %hllog.props
  }

  ; Events 057, 058, 059, 066.
  elseif ($regex(%hllog.cmd, /^("[^"]+") ([^"\x28]+) ("[^"]+") ([^"\x28]+) ("[^"]+")(.*)$/)) {
    var %hllog.firstEvent = $regml(2)
    ; var %hllog.secondEvent = $regml(4)
    var %hllog.firstPlayer = $regml(1)

    if (%hllog.firstEvent == triggered) {
      var %hllog.secondPlayer = $regml(5)
      var %hllog.noun = $remove($regml(3), ")
    }
    else {
      var %hllog.secondPlayer = $regml(3)
      var %hllog.noun = $remove($regml(5), ")
    }

    var %hllog.props = $regml(6)

    aline 1 %hllog.window $+($chr(3), $hllog.teamcolor($hlplayer(%hllog.firstPlayer).team), $hlplayer(%hllog.firstPlayer).name, $chr(15)) %hllog.firstEvent $+($chr(3), $hllog.teamcolor($hlplayer(%hllog.secondPlayer ).team), $hlplayer(%hllog.secondPlayer ).name, $chr(15)) with: $+(", $replace(%hllog.noun, _, $chr(32)), ") $iif($hllog.prop(%hllog.props, headshot), (headshot))
  }

  ; Events 050, 053, 054, 055, 056, 060, 063a, 063b, 068, 069.
  elseif ($regex(%hllog.cmd, /^("[^"]+") ([^"\x28]+) "([^"]+)"(.*)$/)) {
    var %hllog.player = $regml(1)
    var %hllog.event = $regml(2)
    var %hllog.noun = $regml(3)
    var %hllog.props = $regml(4)
    var %hllog.team = $hlplayer(%hllog.player).team

    if (%hllog.event == say) {
      aline 7 %hllog.window $+($chr(3), $hllog.teamcolor(%hllog.team), $hlplayer(%hllog.player).name, $chr(15)) $+(says:, $chr(3), 1) %hllog.noun
    }
    elseif (%hllog.event == say_team) {
      aline 7 %hllog.window $+($chr(3), $hllog.teamcolor(%hllog.team), $hlplayer(%hllog.player).name, $chr(15)) $+(team says:, $chr(3), 1) %hllog.noun
    }
    else {
      aline 1 %hllog.window $+($chr(3), $hllog.teamcolor(%hllog.team), $hlplayer(%hllog.player).name, $chr(15)) %hllog.event $+(", $replace(%hllog.noun, _, $chr(32)), ") %hllog.props
    }
  }

  ; Events 050b, 051, 052.
  elseif ($regex(%hllog.cmd, /^("[^"]+") ([^\x28]+)(.*)$/)) {
    var %hllog.player = $regml(1)
    var %hllog.event = $regml(2)
    ; var %hllog.props = $regml(3)
    var %hllog.team = $hlplayer(%hllog.player).team

    aline 1 %hllog.window $+($chr(3), $hllog.teamcolor(%hllog.team), $hlplayer(%hllog.player).name, $chr(15)) %hllog.event
  }

  ; Events 061, 064.
  elseif ($regex(%hllog.cmd, /^Team "([^"]+)" ([^"\x28]+) "([^"]+)"(.*)$/i)) {
    var %hllog.team = $regml(1)
    var %hllog.event = $regml(2)
    var %hllog.noun = $regml(3)
    ; var %hllog.props = $regml(4)

    aline 1 %hllog.window $+($chr(3), $hllog.teamcolor(%hllog.team), %hllog.team, $chr(15)) %hllog.event $+(", $replace(%hllog.noun, _, $chr(32)), ")
  }

  ; Events 062, 003a, 003b, 005, 006.
  elseif ($regex(%hllog.cmd, /^([^"\x28]+) "([^"]+)"(.*)$/)) {
    var %hllog.event = $regml(1)
    var %hllog.noun = $regml(2)
    var %hllog.props = $regml(3)

    if (%hllog.event == server say) {
      aline 7 %hllog.window Server $+(says:, $chr(3), 1) %hllog.noun
    }
    else {
      aline 1 %hllog.window %hllog.event $+(", $replace(%hllog.noun, _, $chr(32)), ") %hllog.props
    }
  }

  ; Events 001a, 001c, 002a, 002b.
  elseif ($regex(%hllog.cmd, /^([^"\x28]+)(.*)$/)) {
    var %hllog.event = $regml(1)
    ; var %hllog.props = $regml(2)

    aline 1 %hllog.window %hllog.event
  }
}


See also