gltail 0.0.7
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.
- data/History.txt +66 -0
- data/Manifest.txt +40 -0
- data/README +51 -0
- data/README.txt +376 -0
- data/Rakefile +19 -0
- data/TODO +9 -0
- data/bin/gl_tail +109 -0
- data/dist/config.yaml +101 -0
- data/lib/gl_tail.rb +68 -0
- data/lib/gl_tail/activity.rb +145 -0
- data/lib/gl_tail/blob_store.rb +43 -0
- data/lib/gl_tail/block.rb +130 -0
- data/lib/gl_tail/config.rb +187 -0
- data/lib/gl_tail/config/configurable.rb +51 -0
- data/lib/gl_tail/config/yaml_parser.rb +94 -0
- data/lib/gl_tail/element.rb +194 -0
- data/lib/gl_tail/engine.rb +266 -0
- data/lib/gl_tail/font.bin +0 -0
- data/lib/gl_tail/font_store.rb +165 -0
- data/lib/gl_tail/http_helper.rb +58 -0
- data/lib/gl_tail/item.rb +17 -0
- data/lib/gl_tail/parser.rb +46 -0
- data/lib/gl_tail/parsers/apache.rb +56 -0
- data/lib/gl_tail/parsers/iis.rb +47 -0
- data/lib/gl_tail/parsers/mysql.rb +29 -0
- data/lib/gl_tail/parsers/nginx.rb +46 -0
- data/lib/gl_tail/parsers/pix-fwsm.rb +50 -0
- data/lib/gl_tail/parsers/postfix.rb +119 -0
- data/lib/gl_tail/parsers/postgresql.rb +42 -0
- data/lib/gl_tail/parsers/pureftpd.rb +30 -0
- data/lib/gl_tail/parsers/qmail.rb +30 -0
- data/lib/gl_tail/parsers/rails.rb +41 -0
- data/lib/gl_tail/parsers/squid.rb +25 -0
- data/lib/gl_tail/parsers/tshark.rb +25 -0
- data/lib/gl_tail/resolver.rb +69 -0
- data/lib/gl_tail/server.rb +46 -0
- data/lib/gl_tail/sources/base.rb +44 -0
- data/lib/gl_tail/sources/local.rb +12 -0
- data/lib/gl_tail/sources/ssh.rb +112 -0
- data/test/test_gl_tail.rb +0 -0
- metadata +114 -0
data/Rakefile
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
# -*- ruby -*-
|
2
|
+
|
3
|
+
require 'rubygems'
|
4
|
+
require 'hoe'
|
5
|
+
require './lib/gl_tail.rb'
|
6
|
+
|
7
|
+
Hoe.new('gltail', GlTail::VERSION) do |p|
|
8
|
+
p.rubyforge_name = 'gltail'
|
9
|
+
p.author = 'Erlend Simonsen'
|
10
|
+
p.email = 'mr@fudgie.org'
|
11
|
+
p.summary = 'View real-time data and statistics from any logfile on any server with SSH, in an intuitive and entertaining way.'
|
12
|
+
p.description = p.paragraphs_of('README.txt', 2..5).join("\n\n")
|
13
|
+
p.url = p.paragraphs_of('README.txt', 0).first.split(/\n/)[1..-1]
|
14
|
+
p.changes = p.paragraphs_of('History.txt', 0..1).join("\n\n")
|
15
|
+
p.extra_deps << ['ruby-opengl', '>= 0.40.1']
|
16
|
+
p.extra_deps << ['net-ssh', '>= 1.1.2']
|
17
|
+
end
|
18
|
+
|
19
|
+
# vim: syntax=Ruby
|
data/TODO
ADDED
@@ -0,0 +1,9 @@
|
|
1
|
+
Allow more indicators (pulsing color/size, cubes, teapots, etc)
|
2
|
+
Clickable links
|
3
|
+
Drag 'n drop organizing
|
4
|
+
Hide/show blocks with keypresses
|
5
|
+
Limit display to specific host
|
6
|
+
Geolocation on IPS
|
7
|
+
Show only percentage of blobs to handle high-traffic sites
|
8
|
+
Multi-line parsing (MySQL slow-log)
|
9
|
+
Multiple activity providers (local tail, ssh, Splunk)
|
data/bin/gl_tail
ADDED
@@ -0,0 +1,109 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# gl_tail.rb - OpenGL visualization of your server traffic
|
3
|
+
# Copyright 2007 Erlend Simonsen <mr@fudgie.org>
|
4
|
+
#
|
5
|
+
# Licensed under the GNU General Public License v2 (see LICENSE)
|
6
|
+
|
7
|
+
$DBG=0
|
8
|
+
$VRB=1
|
9
|
+
|
10
|
+
file = 'gl_tail.yaml'
|
11
|
+
|
12
|
+
ARGV.each do |arg|
|
13
|
+
case arg
|
14
|
+
when '-help','--help','-h'
|
15
|
+
puts "gl_tail [--help|-h] [--parsers|-p] [--verbose|-v] [--debug|-d] [--debug-ssh|-ds] [configfile]",
|
16
|
+
'[--help|-h] This help screen',
|
17
|
+
'[--version] Print version information',
|
18
|
+
'[--new|-n] Initialize config specified with default options',
|
19
|
+
'[--parsers|-p] List available parsers',
|
20
|
+
'[--options|-o] List available configuration options',
|
21
|
+
'[--quiet|-q] Turn off runtime information',
|
22
|
+
'[--debug|-d] Turn on debugging',
|
23
|
+
'[--debug-ssh|-ds] Only debug SSH',
|
24
|
+
'[configfile] The YAML config file you wish to load (default = config.yaml)'
|
25
|
+
exit
|
26
|
+
when '-version', '--version'
|
27
|
+
@print = :version
|
28
|
+
when '-new', '--new', '-n'
|
29
|
+
@init_config = true
|
30
|
+
when '-parsers','--parsers', '-p'
|
31
|
+
@print = :parsers
|
32
|
+
when '-debug', '--debug', '-d'
|
33
|
+
$DBG=1
|
34
|
+
when '-quiet', '--quiet', '-q'
|
35
|
+
$VRB=0
|
36
|
+
when '-debug-ssh', '--debug-ssh', '-ds'
|
37
|
+
$DBG=2
|
38
|
+
when '--options', '-o'
|
39
|
+
@print = :options
|
40
|
+
else
|
41
|
+
if(File.exist?(arg) && File.file?(arg))
|
42
|
+
file = arg
|
43
|
+
else
|
44
|
+
if defined? @init_config
|
45
|
+
file = arg
|
46
|
+
else
|
47
|
+
file = "#{arg}.yaml"
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
if defined? @init_config
|
54
|
+
require 'ftools'
|
55
|
+
|
56
|
+
if File.directory? file
|
57
|
+
puts "'#{file}' is a directory, not overwriting."
|
58
|
+
exit
|
59
|
+
end
|
60
|
+
|
61
|
+
if File.exist? file
|
62
|
+
File.move(file, file + ".bak")
|
63
|
+
puts "Existing configuration moved to '#{file + '.bak'}'"
|
64
|
+
end
|
65
|
+
|
66
|
+
File.copy(File.dirname(__FILE__) + '/../dist/config.yaml', file)
|
67
|
+
puts "Example configuration installed in '#{file}'"
|
68
|
+
puts "Please edit it and change server and login information."
|
69
|
+
exit
|
70
|
+
elsif !File.exist?(file)
|
71
|
+
puts "Configuration file not found. Either supply the path to a config file as an argument to gl_tail,",
|
72
|
+
"or create a new one with:",
|
73
|
+
" gl_tail --new #{file}"
|
74
|
+
exit
|
75
|
+
end
|
76
|
+
|
77
|
+
require File.dirname(__FILE__) + '/../lib/gl_tail.rb'
|
78
|
+
|
79
|
+
if defined? @print
|
80
|
+
case @print
|
81
|
+
when :parsers
|
82
|
+
puts "Supported Parsers [" + Parser::registry.keys.sort { |a,b| a.to_s <=> b.to_s }.collect{ |p| ":#{p.to_s}"}.join(", ") + "]"
|
83
|
+
when :options
|
84
|
+
require 'pp'
|
85
|
+
puts "Supported Configuration Options"
|
86
|
+
|
87
|
+
pp(GlTail::CONFIG_OPTIONS)
|
88
|
+
when :version
|
89
|
+
puts "gl_tail v" + GlTail::VERSION + " by Erlend Simonsen <mr@fudgie.org> - http://www.fudgie.org"
|
90
|
+
end
|
91
|
+
exit
|
92
|
+
end
|
93
|
+
|
94
|
+
|
95
|
+
######## TRAP Interrupts and exit cleanly ########
|
96
|
+
|
97
|
+
trap("HUP") { exit }
|
98
|
+
trap("INT") { exit }
|
99
|
+
trap("QUIT") { exit }
|
100
|
+
trap("ABRT") { exit }
|
101
|
+
trap("KILL") { exit }
|
102
|
+
trap("TERM") { exit }
|
103
|
+
#trap("USR1") { $VRB >= 1 ? $VRB = 0 : $VRB += 1; puts "verbose toggled" }
|
104
|
+
trap("USR2") { $DBG >= 2 ? $DBG = 0 : $DBG += 1; puts "debug level toggled" }
|
105
|
+
|
106
|
+
config = GlTail::Config.parse_yaml(file)
|
107
|
+
|
108
|
+
engine = GlTail::Engine.new(config)
|
109
|
+
engine.start
|
data/dist/config.yaml
ADDED
@@ -0,0 +1,101 @@
|
|
1
|
+
servers:
|
2
|
+
site1:
|
3
|
+
host: foobar.com
|
4
|
+
user: foo
|
5
|
+
password: topsecret
|
6
|
+
command: tail -f -n0
|
7
|
+
files: /var/log/apache/access_log
|
8
|
+
parser: apache
|
9
|
+
color: 0.2, 1.0, 0.2, 1.0
|
10
|
+
rails:
|
11
|
+
host: anotherfunsite.com
|
12
|
+
user: anotherfunuser
|
13
|
+
port: 222
|
14
|
+
command: tail -f -n0
|
15
|
+
files: /var/www/apps/funapp/current/log/production.log
|
16
|
+
parser: rails
|
17
|
+
color: 0.2, 0.2, 1.0, 1.0
|
18
|
+
config:
|
19
|
+
dimensions: 1200x600
|
20
|
+
min_blob_size: 0.004
|
21
|
+
max_blob_size: 0.04
|
22
|
+
highlight_color: orange
|
23
|
+
bounce: false
|
24
|
+
left_column:
|
25
|
+
size: 25
|
26
|
+
alignment: -0.99
|
27
|
+
blocks:
|
28
|
+
info:
|
29
|
+
order: 0
|
30
|
+
size: 10
|
31
|
+
auto_clean: false
|
32
|
+
show: total
|
33
|
+
hosts:
|
34
|
+
order: 1
|
35
|
+
size: 3
|
36
|
+
sites:
|
37
|
+
order: 2
|
38
|
+
size: 10
|
39
|
+
content:
|
40
|
+
order: 3
|
41
|
+
size: 5
|
42
|
+
show: total
|
43
|
+
color: 1.0, 0.8, 0.4, 1.0
|
44
|
+
status:
|
45
|
+
order: 4
|
46
|
+
size: 10
|
47
|
+
color: 1.0, 0.8, 0.4, 1.0
|
48
|
+
types:
|
49
|
+
order: 5
|
50
|
+
size: 5
|
51
|
+
color: 1.0, 0.4, 0.2, 1.0
|
52
|
+
users:
|
53
|
+
order: 6
|
54
|
+
size: 10
|
55
|
+
smtp:
|
56
|
+
order: 7
|
57
|
+
size: 5
|
58
|
+
logins:
|
59
|
+
order: 8
|
60
|
+
size: 5
|
61
|
+
database:
|
62
|
+
order: 9
|
63
|
+
size: 10
|
64
|
+
|
65
|
+
right_column:
|
66
|
+
size: 25
|
67
|
+
alignment: 0.99
|
68
|
+
blocks:
|
69
|
+
urls:
|
70
|
+
order: 0
|
71
|
+
size: 15
|
72
|
+
slow requests:
|
73
|
+
order: 1
|
74
|
+
size: 5
|
75
|
+
show: average
|
76
|
+
referrers:
|
77
|
+
order: 2
|
78
|
+
size: 10
|
79
|
+
user agents:
|
80
|
+
order: 3
|
81
|
+
size: 5
|
82
|
+
color: 1.0, 1.0, 1.0, 1.0
|
83
|
+
mail from:
|
84
|
+
order: 4
|
85
|
+
size: 5
|
86
|
+
mail to:
|
87
|
+
order: 5
|
88
|
+
size: 5
|
89
|
+
viruses:
|
90
|
+
order: 6
|
91
|
+
size: 5
|
92
|
+
rejections:
|
93
|
+
order: 7
|
94
|
+
size: 5
|
95
|
+
color: 1.0, 0.2, 0.2, 1.0
|
96
|
+
warnings:
|
97
|
+
order: 8
|
98
|
+
size: 5
|
99
|
+
resolver:
|
100
|
+
reverse_ip_lookups: true
|
101
|
+
reverse_timeout: 0.5
|
data/lib/gl_tail.rb
ADDED
@@ -0,0 +1,68 @@
|
|
1
|
+
# gl_tail.rb - OpenGL visualization of your server traffic
|
2
|
+
# Copyright 2007 Erlend Simonsen <mr@fudgie.org>
|
3
|
+
#
|
4
|
+
# Licensed under the General Public License v2 (see LICENSE)
|
5
|
+
#
|
6
|
+
|
7
|
+
module GlTail
|
8
|
+
VERSION = '0.0.7'
|
9
|
+
end
|
10
|
+
|
11
|
+
begin
|
12
|
+
require 'rubygems'
|
13
|
+
rescue LoadError
|
14
|
+
puts "Rubygems missing. Please install."
|
15
|
+
puts "Ubuntu:\n sudo apt-get install rubygems"
|
16
|
+
end
|
17
|
+
|
18
|
+
gem_version = Gem::RubyGemsVersion.split('.')
|
19
|
+
|
20
|
+
if gem_version[1].to_i < 9 || (gem_version[1].to_i >= 9 && gem_version[2].to_i < 2)
|
21
|
+
puts "rubygems too old to build ruby-opengl. Please update."
|
22
|
+
puts "Ubuntu:"
|
23
|
+
puts " sudo gem update --system"
|
24
|
+
exit
|
25
|
+
end
|
26
|
+
|
27
|
+
begin
|
28
|
+
gem 'ruby-opengl', '>= 0.40.1'
|
29
|
+
require 'gl'
|
30
|
+
require 'glut'
|
31
|
+
rescue LoadError
|
32
|
+
puts "Missing or outdated gem: ruby-opengl (>=0.40.1)"
|
33
|
+
puts "Ubuntu:"
|
34
|
+
puts " sudo apt-get install rake ruby1.8-dev libgl1-mesa-dev libglu1-mesa-dev libglut3-dev"
|
35
|
+
puts " sudo gem install -y ruby-opengl -r"
|
36
|
+
puts "\nFor more information: http://ruby-opengl.rubyforge.org/build_install.html"
|
37
|
+
exit
|
38
|
+
end
|
39
|
+
|
40
|
+
begin
|
41
|
+
gem 'net-ssh'
|
42
|
+
require 'net/ssh'
|
43
|
+
rescue LoadError
|
44
|
+
puts "Missing gem net-ssh."
|
45
|
+
puts "Ubuntu:"
|
46
|
+
puts " sudo gem install -y net-ssh -r"
|
47
|
+
exit
|
48
|
+
end
|
49
|
+
|
50
|
+
$:.unshift(File.dirname(__FILE__)) # this should be obsolete once its a gem
|
51
|
+
|
52
|
+
# load our libraries
|
53
|
+
require 'gl_tail/engine'
|
54
|
+
require 'gl_tail/config/configurable'
|
55
|
+
require 'gl_tail/config'
|
56
|
+
require 'gl_tail/config/yaml_parser'
|
57
|
+
|
58
|
+
# sources represent event sources defaults to ssh tail
|
59
|
+
# future options: JMS queue, spread.org, local tail, etc
|
60
|
+
require 'gl_tail/sources/base'
|
61
|
+
require 'gl_tail/sources/ssh'
|
62
|
+
|
63
|
+
%w( engine activity block item element parser resolver blob_store font_store).each {|f| require "gl_tail/#{f}" }
|
64
|
+
|
65
|
+
Dir.glob( "#{File.dirname(__FILE__)}/gl_tail/parsers/*.rb" ).each {|f| require f }
|
66
|
+
|
67
|
+
|
68
|
+
|
@@ -0,0 +1,145 @@
|
|
1
|
+
# gl_tail.rb - OpenGL visualization of your server traffic
|
2
|
+
# Copyright 2007 Erlend Simonsen <mr@fudgie.org>
|
3
|
+
#
|
4
|
+
# Licensed under the GNU General Public License v2 (see LICENSE)
|
5
|
+
#
|
6
|
+
|
7
|
+
class Activity
|
8
|
+
attr_accessor :x, :y, :z, :wx, :wy, :wz, :xi, :yi, :zi
|
9
|
+
attr_accessor :message, :color, :size, :type
|
10
|
+
|
11
|
+
def initialize(message, x, y, z, color, size, type = 0)
|
12
|
+
@message = message
|
13
|
+
@x, @y, @z = x, y, z
|
14
|
+
@xi, @yi, @zi = 0.012 + (rand(100)/100.0 ) * 0.0012 , 0.002 + (rand(1000)/1000.0 ) * 0.002, 0
|
15
|
+
# @xi, @yi, @zi = 0.015 , 0.0025, 0
|
16
|
+
|
17
|
+
if @x >= 0.0
|
18
|
+
@xi = -@xi
|
19
|
+
end
|
20
|
+
|
21
|
+
@xi = (rand(100)/100.0 * 0.02) - 0.01 if type == 2
|
22
|
+
|
23
|
+
@color = color
|
24
|
+
@size = size
|
25
|
+
@type = type
|
26
|
+
|
27
|
+
@rx, @ry, @rz = rand(360), rand(360), 0
|
28
|
+
end
|
29
|
+
|
30
|
+
def render(engine)
|
31
|
+
if @type != 5
|
32
|
+
if engine.screen.wanted_fps == 0
|
33
|
+
@x += @xi/2
|
34
|
+
@y += @yi/2
|
35
|
+
@yi = @yi - 0.0005/2
|
36
|
+
else
|
37
|
+
@fps_mod ||= (60.0 / engine.screen.wanted_fps)
|
38
|
+
@x += (@xi/2) * @fps_mod
|
39
|
+
@y += (@yi/2) * @fps_mod
|
40
|
+
@yi = @yi - (0.0005/2) * @fps_mod
|
41
|
+
end
|
42
|
+
|
43
|
+
# @yi = @yi * 1.01
|
44
|
+
# @xi = @xi * 0.9995
|
45
|
+
|
46
|
+
if @y - @size/2 < -engine.screen.top
|
47
|
+
@y = -engine.screen.top + @size/2
|
48
|
+
@yi = -@yi * 0.7
|
49
|
+
@x = 30.0 if(@type == 2 || (engine.screen.bounce.nil? || engine.screen.bounce == false ) )
|
50
|
+
end
|
51
|
+
else
|
52
|
+
dy = @wy - @y
|
53
|
+
if dy.abs < 0.001
|
54
|
+
@y = @wy
|
55
|
+
else
|
56
|
+
@y += dy / 20
|
57
|
+
end
|
58
|
+
|
59
|
+
dx = @wx - @x
|
60
|
+
if dx.abs < 0.001
|
61
|
+
@x = @wx
|
62
|
+
else
|
63
|
+
@x += dx / 20
|
64
|
+
end
|
65
|
+
|
66
|
+
if @x == @wx
|
67
|
+
@x = 20.0
|
68
|
+
end
|
69
|
+
|
70
|
+
end
|
71
|
+
|
72
|
+
glPushMatrix()
|
73
|
+
glColor(@color)
|
74
|
+
|
75
|
+
if @type == 0 || @type == 5
|
76
|
+
glTranslate(@x, @y, @z)
|
77
|
+
if engine.screen.mode == 1
|
78
|
+
glRotatef(@rx, 1.0, 0.0, 0.0)
|
79
|
+
glRotatef(@ry, 0.0, 1.0, 0.0)
|
80
|
+
@rx += 2
|
81
|
+
@ry += 1
|
82
|
+
unless BlobStore.has(@size)
|
83
|
+
list = glGenLists(1)
|
84
|
+
glNewList(list, GL_COMPILE)
|
85
|
+
|
86
|
+
glBegin(GL_QUADS)
|
87
|
+
glVertex3f(-@size, @size, 0)
|
88
|
+
glVertex3f( @size, @size, 0)
|
89
|
+
glVertex3f( @size, -@size, 0)
|
90
|
+
glVertex3f(-@size, -@size, 0)
|
91
|
+
glEnd
|
92
|
+
|
93
|
+
glEndList()
|
94
|
+
BlobStore.put(@size,list)
|
95
|
+
end
|
96
|
+
else
|
97
|
+
unless BlobStore.has(@size)
|
98
|
+
|
99
|
+
list = glGenLists(1)
|
100
|
+
glNewList(list, GL_COMPILE)
|
101
|
+
|
102
|
+
tmp = 10 + 10 * ((@size-engine.screen.min_blob_size)/engine.screen.max_blob_size)
|
103
|
+
if not tmp
|
104
|
+
puts "THIS KEEPS CRASHING FOR ME WITH tmp == NaN -- cant figure out why"
|
105
|
+
tmp = 2
|
106
|
+
end
|
107
|
+
|
108
|
+
glutSolidSphere(@size, tmp, 2)
|
109
|
+
glEndList()
|
110
|
+
BlobStore.put(@size,list)
|
111
|
+
end
|
112
|
+
end
|
113
|
+
glCallList(BlobStore.get(@size))
|
114
|
+
elsif @type == 1
|
115
|
+
glTranslate(@x, @y, @z)
|
116
|
+
glRotatef(@rx, 1.0, 0.0, 0.0)
|
117
|
+
glRotatef(@ry, 0.0, 1.0, 0.0)
|
118
|
+
@rx += 2
|
119
|
+
@ry += 1
|
120
|
+
unless BlobStore.has(@size.to_s)
|
121
|
+
list = glGenLists(1)
|
122
|
+
glNewList(list, GL_COMPILE)
|
123
|
+
|
124
|
+
glBegin(GL_QUADS)
|
125
|
+
glVertex3f(-@size, @size, 0)
|
126
|
+
glVertex3f( @size, @size, 0)
|
127
|
+
glVertex3f( @size, -@size, 0)
|
128
|
+
glVertex3f(-@size, -@size, 0)
|
129
|
+
glEnd
|
130
|
+
|
131
|
+
glEndList()
|
132
|
+
BlobStore.put(@size.to_s,list)
|
133
|
+
end
|
134
|
+
|
135
|
+
glCallList(BlobStore.get(@size.to_s))
|
136
|
+
elsif @type == 2
|
137
|
+
glTranslate(@x, @y, @z)
|
138
|
+
glRasterPos(0.0, 0.0)
|
139
|
+
|
140
|
+
engine.render_string(@message)
|
141
|
+
end
|
142
|
+
|
143
|
+
glPopMatrix()
|
144
|
+
end
|
145
|
+
end
|