log_sense 1.2.3 → 1.3.4
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/CHANGELOG.org +13 -6
- data/Gemfile.lock +1 -3
- data/README.org +53 -35
- data/apache-screenshot.png +0 -0
- data/lib/log_sense/apache_log_line_parser.rb +56 -0
- data/lib/log_sense/apache_log_parser.rb +14 -12
- data/lib/log_sense/templates/_output_table.html.erb +15 -11
- data/lib/log_sense/templates/_report_data.html.erb +12 -0
- data/lib/log_sense/templates/apache.html.erb +11 -18
- data/lib/log_sense/templates/rails.html.erb +8 -16
- data/lib/log_sense/version.rb +1 -1
- data/lib/log_sense.rb +1 -0
- data/log_sense.gemspec +20 -21
- metadata +16 -27
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a8250028b7a7038e07f2bd9fa069bfdf0ab1815a8711a0b6971a91030d529882
|
4
|
+
data.tar.gz: 236e1ba2c3ada9272f1e7eaa649cd1664776da933a90e41b6e70fffbbe002043
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 72b6284cd6f09ebf16c4fe34fc7098da44e993a2946fb09f72ccaa7898eb462b9fcb49ce2e37e06b206a3f00650f8a033ec034ffeeab3afe587b6b607d079302
|
7
|
+
data.tar.gz: 6b96590430caa4e9717180c1812b0227b661f1fef4c99e10515da6da8acbe8fd596b91a9e0d536eff2ce525ba1fc01f4819a5c3f649bb59f4c77754edbbd5b0c
|
data/CHANGELOG.org
CHANGED
@@ -2,13 +2,20 @@
|
|
2
2
|
#+AUTHOR: Adolfo Villafiorita
|
3
3
|
#+STARTUP: showall
|
4
4
|
|
5
|
-
*
|
6
|
-
<2021-12-17 Fri>
|
5
|
+
* 1.3.2
|
7
6
|
|
8
|
-
-
|
7
|
+
- [Code] HTML reports now generate JSON data which is shared between
|
8
|
+
DataTable and Vega Light: this should reduce page size and loading
|
9
|
+
time of HTML reports
|
10
|
+
- [Doc] Added screenshot and fixed some text
|
11
|
+
- [Doc] Fixes requirements on Ruby version
|
9
12
|
|
10
|
-
*
|
11
|
-
<2021-12-17 Fri>
|
13
|
+
* 1.3.1
|
12
14
|
|
13
|
-
-
|
15
|
+
- [Code] Strengthened parsing of Apache Logs (added WebDav and other methods)
|
14
16
|
|
17
|
+
* 1.3.0
|
18
|
+
|
19
|
+
- [Code] Removed dependency from =apache_log-parser= and implemented our own
|
20
|
+
parser for the combined format.
|
21
|
+
|
data/Gemfile.lock
CHANGED
@@ -1,8 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
log_sense (1.
|
5
|
-
apache_log-parser
|
4
|
+
log_sense (1.3.1)
|
6
5
|
browser
|
7
6
|
ipaddr
|
8
7
|
iso_country_codes
|
@@ -12,7 +11,6 @@ PATH
|
|
12
11
|
GEM
|
13
12
|
remote: https://rubygems.org/
|
14
13
|
specs:
|
15
|
-
apache_log-parser (3.1.2)
|
16
14
|
browser (5.3.1)
|
17
15
|
byebug (11.1.3)
|
18
16
|
ipaddr (1.2.3)
|
data/README.org
CHANGED
@@ -4,24 +4,10 @@
|
|
4
4
|
|
5
5
|
* Introduction
|
6
6
|
|
7
|
-
LogSense generates reports and statistics from Apache
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
LogSense moves along the lines of tools such as [[https://goaccess.io/][GoAccess]]
|
13
|
-
and [[https://umami.is/][Umami]], focusing on privacy and data-ownership: the data
|
14
|
-
generated by LogSense is stored on your computer and owned by
|
15
|
-
you (like it should be).
|
16
|
-
|
17
|
-
LogSense is also inspired by *static websites generators*: statistics
|
18
|
-
are generated from the command line and accessed as static HTML files.
|
19
|
-
By generating static resources, LogSense significantly reduces the
|
20
|
-
attack surface of your webserver and installation headaches.
|
21
|
-
|
22
|
-
We have, for instance, a cron job running on our servers, generating
|
23
|
-
statistics at night. The generated files are then made available on a
|
24
|
-
private area on the web.
|
7
|
+
LogSense generates reports and statistics from Apache and Ruby on
|
8
|
+
Rails logs. Written in Ruby, it runs from the command line, it is
|
9
|
+
fast, and it can be installed on any system with a relatively recent
|
10
|
+
version of Ruby. We tested on Ruby 2.6.9, Ruby 3.0.x and later.
|
25
11
|
|
26
12
|
LogSense reports the following data:
|
27
13
|
|
@@ -40,7 +26,27 @@ LogSense reports the following data:
|
|
40
26
|
Filters from the command line allow to analyze specific periods and
|
41
27
|
distinguish traffic generated by self polls and crawlers.
|
42
28
|
|
43
|
-
LogSense generates HTML, txt
|
29
|
+
LogSense generates HTML, txt, and SQLite outputs.
|
30
|
+
|
31
|
+
And, of course, the compulsory screenshot:
|
32
|
+
|
33
|
+
#+ATTR_HTML: :width 80%
|
34
|
+
[[file:./apache-screenshot.png]]
|
35
|
+
|
36
|
+
* Motivation
|
37
|
+
|
38
|
+
LogSense moves along the lines of tools such as [[https://goaccess.io/][GoAccess]] (which
|
39
|
+
strongly inspired the development of Log Sense) and [[https://umami.is/][Umami]], focusing on
|
40
|
+
*privacy* and *data-ownership*: the data generated by LogSense is
|
41
|
+
stored on your computer and owned by you (like it should be)[fn:1].
|
42
|
+
|
43
|
+
LogSense is also inspired by *static websites generators*: statistics
|
44
|
+
are generated from the command line and accessed as static HTML files.
|
45
|
+
LogSense thus significantly reduces the attack surface of your
|
46
|
+
web server and installation headaches. We have, for instance, a cron
|
47
|
+
job running on our servers, generating statistics at night. The
|
48
|
+
generated files are then made available on a private area on the web.
|
49
|
+
|
44
50
|
|
45
51
|
* Installation
|
46
52
|
|
@@ -70,48 +76,60 @@ LogSense generates HTML, txt (Org Mode), and SQLite outputs.
|
|
70
76
|
-v, --version Prints version information
|
71
77
|
-h, --help Prints this help
|
72
78
|
|
73
|
-
This is version 1.
|
79
|
+
This is version 1.3.1
|
74
80
|
|
75
81
|
Output formats
|
76
|
-
apache parsing can produce the following outputs:
|
77
|
-
- sqlite
|
78
|
-
- html
|
79
82
|
rails parsing can produce the following outputs:
|
80
83
|
- sqlite
|
81
84
|
- txt
|
85
|
+
- html
|
86
|
+
apache parsing can produce the following outputs:
|
87
|
+
- sqlite
|
88
|
+
- html
|
82
89
|
#+end_example
|
83
90
|
|
91
|
+
Examples:
|
92
|
+
|
93
|
+
#+begin_example sh
|
94
|
+
log_sense -f apache -i access.log -t txt > access-data.txt
|
95
|
+
log_sense -f rails -i production.log -t html -o performance.txt
|
96
|
+
#+end_example
|
97
|
+
|
84
98
|
* Change Log
|
85
99
|
|
86
100
|
See the [[file:CHANGELOG.org][CHANGELOG]] file.
|
87
101
|
|
88
102
|
* Compatibility
|
89
103
|
|
90
|
-
LogSense should run on any system on which Ruby
|
104
|
+
LogSense should run on any system on which a recent version of Ruby
|
105
|
+
runs. We tested it with Ruby 2.6.9 and Ruby 3.x.x.
|
91
106
|
|
92
107
|
Concerning the outputs:
|
93
108
|
|
94
|
-
-
|
95
|
-
are downloaded from a CDN
|
96
|
-
- The textual format is compatible with Org Mode and can be further
|
97
|
-
processed to any format Org Mode can be exported to (including HTML
|
98
|
-
and PDF)
|
109
|
+
- HTML reports use [[https://get.foundation/][Zurb Foundation]], [[https://www.datatables.net/][Data Tables]], and [[https://vega.github.io/vega-lite/][Vega Light]], which
|
110
|
+
are all downloaded from a CDN
|
111
|
+
- The textual format is compatible with [[https://orgmode.org/][Org Mode]] and can be further
|
112
|
+
processed to any format [[https://orgmode.org/][Org Mode]] can be exported to (including HTML
|
113
|
+
and PDF)
|
99
114
|
|
100
115
|
* Author and Contributors
|
101
116
|
|
102
|
-
[[
|
117
|
+
[[https://shair.tech][Shair.Tech]]
|
103
118
|
|
104
119
|
* Known Bugs
|
105
120
|
|
106
|
-
|
107
|
-
|
121
|
+
No known bugs; an unknown number of unknown bugs.
|
108
122
|
(See the open issues for the known bugs.)
|
109
123
|
|
110
124
|
* License
|
111
125
|
|
112
126
|
Distributed under the terms of the [[http://opensource.org/licenses/MIT][MIT License]].
|
113
127
|
|
114
|
-
Geolocation is made possible by the DB-IP.com IP to City database,
|
115
|
-
a CC license.
|
116
|
-
|
128
|
+
Geolocation is made possible by the DB-IP.com IP to City database,
|
129
|
+
released under a CC license.
|
117
130
|
|
131
|
+
[fn:1] There is a small catch: CSS and JavaScript for layout and plots
|
132
|
+
are downloaded from a CDN. Technically, thus, if you generate HTML
|
133
|
+
reports and open them, a request is performed and the CDN might keep a
|
134
|
+
track (see [[https://en.wikipedia.org/wiki/Content_delivery_network#Security_and_privacy][CDN Security and Privacy on Wikipedia]] for more details).
|
135
|
+
Textual reports don't have this issue.
|
Binary file
|
@@ -0,0 +1,56 @@
|
|
1
|
+
module LogSense
|
2
|
+
class ApacheLogLineParser
|
3
|
+
# parses a query and makes it into an expression which can be evaluated
|
4
|
+
# LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-agent}i\"" combined
|
5
|
+
#
|
6
|
+
# %h: IP
|
7
|
+
# %l: ident or -
|
8
|
+
# %u: userid or -
|
9
|
+
# %t: [10/Oct/2000:13:55:36 -0700]
|
10
|
+
# day = 2*digit
|
11
|
+
# month = 3*letter
|
12
|
+
# year = 4*digit
|
13
|
+
# hour = 2*digit
|
14
|
+
# minute = 2*digit
|
15
|
+
# second = 2*digit
|
16
|
+
# zone = (`+' | `-') 4*digit
|
17
|
+
# %r: GET /apache_pb.gif HTTP/1.0
|
18
|
+
# %{User-agent}: "
|
19
|
+
#
|
20
|
+
# 116.179.32.16 - - [19/Dec/2021:22:35:11 +0100] "GET / HTTP/1.1" 200 135 "-" "Mozilla/5.0 (compatible; Baiduspider/2.0; +http://www.baidu.com/search/spider.html)"
|
21
|
+
|
22
|
+
DAY = /[0-9]{2}/
|
23
|
+
MONTH = /[A-Za-z]{3}/
|
24
|
+
YEAR = /[0-9]{4}/
|
25
|
+
TIMEC = /[0-9]{2}/
|
26
|
+
TIMEZONE = /(\+|-)[0-9]{4}/
|
27
|
+
|
28
|
+
IP = /(?<ip>[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}|::1)/
|
29
|
+
IDENT = /(?<ident>[^ ]+|-)/
|
30
|
+
USERID = /(?<userid>[^ ]+|-)/
|
31
|
+
|
32
|
+
TIMESTAMP = /(?<date>#{DAY}\/#{MONTH}\/#{YEAR}):(?<time>#{TIMEC}:#{TIMEC}:#{TIMEC} #{TIMEZONE})/
|
33
|
+
|
34
|
+
HTTP_METHODS=/GET|HEAD|POST|PUT|DELETE|CONNECT|OPTIONS|TRACE|PATCH/
|
35
|
+
WEBDAV_METHODS=/COPY|LOCK|MKCOL|MOVE|PROPFIND|PROPPATCH|UNLOCK/
|
36
|
+
OTHER_METHODS=/SEARCH|REPORT/
|
37
|
+
METHOD=/(?<method>#{HTTP_METHODS}|#{WEBDAV_METHODS}|#{OTHER_METHODS})/
|
38
|
+
PROTOCOL=/(?<protocol>HTTP\/[0-9]\.[0-9])/
|
39
|
+
URL=/(?<url>[^ ]+)/
|
40
|
+
REFERER=/(?<referer>[^ ]+)/
|
41
|
+
RETURN_CODE=/(?<status>[1-5][0-9][0-9])/
|
42
|
+
SIZE=/(?<size>[0-9]+|-)/
|
43
|
+
|
44
|
+
USER_AGENT = /(?<user_agent>[^"]+)/
|
45
|
+
|
46
|
+
attr_reader :format
|
47
|
+
|
48
|
+
def initialize
|
49
|
+
@format = /#{IP} #{IDENT} #{USERID} \[#{TIMESTAMP}\] "#{METHOD} #{URL} #{PROTOCOL}" #{RETURN_CODE} #{SIZE} "#{REFERER}" "#{USER_AGENT}"/
|
50
|
+
end
|
51
|
+
|
52
|
+
def parse line
|
53
|
+
hash = @format.match(line) || raise("Apache LogLine Parser Error: Could not parse #{line}")
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
@@ -1,4 +1,3 @@
|
|
1
|
-
require 'apache_log/parser'
|
2
1
|
require 'sqlite3'
|
3
2
|
require 'browser'
|
4
3
|
|
@@ -50,21 +49,20 @@ module LogSense
|
|
50
49
|
platform_version)
|
51
50
|
values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)')
|
52
51
|
|
53
|
-
parser =
|
52
|
+
parser = ApacheLogLineParser.new
|
54
53
|
|
55
54
|
content.each do |line|
|
56
55
|
begin
|
57
56
|
hash = parser.parse line
|
58
|
-
|
59
57
|
ua = Browser.new(hash[:user_agent], accept_language: "en-us")
|
60
58
|
ins.execute(
|
61
|
-
hash[:
|
62
|
-
hash[:
|
63
|
-
hash[:
|
64
|
-
hash
|
65
|
-
hash[:
|
66
|
-
hash[:
|
67
|
-
(hash[:
|
59
|
+
DateTime.parse("#{hash[:date]}T#{hash[:time]}").iso8601,
|
60
|
+
hash[:ip],
|
61
|
+
hash[:userid],
|
62
|
+
unique_visitor_id(hash),
|
63
|
+
hash[:method],
|
64
|
+
hash[:url],
|
65
|
+
(hash[:url] ? File.extname(hash[:url]) : ""),
|
68
66
|
hash[:status],
|
69
67
|
hash[:size].to_i,
|
70
68
|
hash[:referer],
|
@@ -75,13 +73,17 @@ module LogSense
|
|
75
73
|
(ua.platform.name || ""),
|
76
74
|
(ua.platform.version || "")
|
77
75
|
)
|
78
|
-
rescue
|
79
|
-
STDERR.puts
|
76
|
+
rescue StandardError => e
|
77
|
+
STDERR.puts e.message
|
80
78
|
end
|
81
79
|
end
|
82
80
|
|
83
81
|
db
|
84
82
|
end
|
85
83
|
|
84
|
+
def self.unique_visitor_id hash
|
85
|
+
"#{hash[:date]} #{hash[:ip]} #{hash[:user_agent]}"
|
86
|
+
end
|
87
|
+
|
86
88
|
end
|
87
89
|
end
|
@@ -4,22 +4,26 @@ def slugify string
|
|
4
4
|
end
|
5
5
|
%>
|
6
6
|
|
7
|
-
<table id="
|
7
|
+
<table id="table-<%= index %>" class="table unstriped">
|
8
8
|
<thead>
|
9
9
|
<tr>
|
10
|
-
<% header.each do |
|
11
|
-
<th
|
10
|
+
<% report[:header].each do |header| %>
|
11
|
+
<th><%= header %></th>
|
12
12
|
<% end %>
|
13
13
|
</tr>
|
14
14
|
</thead>
|
15
15
|
<tbody>
|
16
|
-
<% rows.each do |row| %>
|
17
|
-
<tr>
|
18
|
-
<% row.each_with_index do |cell, i| %>
|
19
|
-
<td class="<%= slugify (header[i] || "") %>"><%= cell %></td>
|
20
|
-
<% end %>
|
21
|
-
</tr>
|
22
|
-
<% end %>
|
23
16
|
</tbody>
|
24
17
|
</table>
|
25
|
-
|
18
|
+
<script>
|
19
|
+
$(document).ready(function(){
|
20
|
+
$('#table-<%= index %>').dataTable({
|
21
|
+
data: data_<%= index %>,
|
22
|
+
columns: [
|
23
|
+
<% report[:header].each do |header| %>
|
24
|
+
{ data: '<%= header %>', className: '<%= slugify(header) %>' },
|
25
|
+
<% end %>
|
26
|
+
]
|
27
|
+
});
|
28
|
+
});
|
29
|
+
</script>
|
@@ -0,0 +1,12 @@
|
|
1
|
+
<script>
|
2
|
+
/* this is used both by Vega and DataTable */
|
3
|
+
data_<%= index %> = [
|
4
|
+
<% report[:rows].each do |row| %>
|
5
|
+
{
|
6
|
+
<% report[:header].each_with_index do |h, i| %>
|
7
|
+
"<%= h %>": <%= (row[i].class == Integer or row[i].class == Float) ? row[i] : "\"#{row[i]}\"" %>,
|
8
|
+
<% end %>
|
9
|
+
},
|
10
|
+
<% end %>
|
11
|
+
]
|
12
|
+
</script>
|
@@ -17,6 +17,8 @@
|
|
17
17
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/foundation-sites@6.7.4/dist/css/foundation.min.css">
|
18
18
|
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.css"/>
|
19
19
|
|
20
|
+
<script type="text/javascript" src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
|
21
|
+
<script type="text/javascript" src="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.js"></script>
|
20
22
|
|
21
23
|
<script src="https://cdn.jsdelivr.net/npm/vega@5.21.0"></script>
|
22
24
|
<script src="https://cdn.jsdelivr.net/npm/vega-lite@5.2.0"></script>
|
@@ -29,14 +31,14 @@
|
|
29
31
|
}
|
30
32
|
|
31
33
|
#offCanvas {
|
32
|
-
color:
|
33
|
-
background: #
|
34
|
+
color: #DEDEDE;
|
35
|
+
background: #1C1C1C;
|
34
36
|
border-right: none;
|
35
37
|
box-shadow: none;
|
36
38
|
padding: 0.5rem;
|
37
39
|
}
|
38
40
|
#offCanvas a {
|
39
|
-
color: #
|
41
|
+
color: #FFFFFF;
|
40
42
|
}
|
41
43
|
|
42
44
|
.contents-button {
|
@@ -69,7 +71,7 @@
|
|
69
71
|
|
70
72
|
.card-divider {
|
71
73
|
padding: 0.2rem 0.4rem 0.2rem 0.4rem;
|
72
|
-
background: #
|
74
|
+
background: #1C1C1C;
|
73
75
|
color: white;
|
74
76
|
}
|
75
77
|
|
@@ -426,7 +428,7 @@
|
|
426
428
|
<%= report[:title] %>
|
427
429
|
</h2>
|
428
430
|
</div>
|
429
|
-
|
431
|
+
<%= render "report_data.html.erb", report: report, index: index %>
|
430
432
|
<% if report[:vega_spec] %>
|
431
433
|
<div id="<%= "plot-#{index}" %>"></div>
|
432
434
|
<script>
|
@@ -436,22 +438,15 @@
|
|
436
438
|
width: "container",
|
437
439
|
description: "<%= report[:title] %>",
|
438
440
|
data: {
|
439
|
-
values:
|
440
|
-
<% report[:rows].each do |row| %>
|
441
|
-
{
|
442
|
-
<% report[:header].each_with_index do |h, i| %>
|
443
|
-
"<%= h %>": <%= (row[i].class == Integer or row[i].class == Float) ? row[i] : "\"#{row[i]}\"" %>,
|
444
|
-
<% end %>
|
445
|
-
},
|
446
|
-
<% end %>
|
447
|
-
]
|
441
|
+
values: data_<%= index %>
|
448
442
|
},
|
449
443
|
});
|
450
444
|
vegaEmbed('#<%= "plot-#{index}"%>', plot_spec_<%= index %>);
|
451
445
|
</script>
|
452
446
|
<% end %>
|
453
|
-
|
454
|
-
|
447
|
+
|
448
|
+
<div class="card-section">
|
449
|
+
<%= render "output_table.html.erb", report: report, index: index %>
|
455
450
|
</div>
|
456
451
|
</article>
|
457
452
|
<% end %>
|
@@ -569,9 +564,7 @@
|
|
569
564
|
</section>
|
570
565
|
</div>
|
571
566
|
|
572
|
-
<script type="text/javascript" src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
|
573
567
|
<script type="text/javascript" src="js/vendor/what-input.js"></script>
|
574
|
-
<script type="text/javascript" src="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.js"></script>
|
575
568
|
<script src="https://cdn.jsdelivr.net/npm/vega@5"></script>
|
576
569
|
<script type="text/javascript" src="https://cdn.jsdelivr.net/npm/foundation-sites@6.7.4/dist/js/foundation.min.js" crossorigin="anonymous"></script>
|
577
570
|
<script>
|
@@ -17,6 +17,8 @@
|
|
17
17
|
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/foundation-sites@6.7.4/dist/css/foundation.min.css">
|
18
18
|
<link rel="stylesheet" type="text/css" href="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.css"/>
|
19
19
|
|
20
|
+
<script type="text/javascript" src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
|
21
|
+
<script type="text/javascript" src="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.js"></script>
|
20
22
|
|
21
23
|
<script src="https://cdn.jsdelivr.net/npm/vega@5.21.0"></script>
|
22
24
|
<script src="https://cdn.jsdelivr.net/npm/vega-lite@5.2.0"></script>
|
@@ -29,14 +31,14 @@
|
|
29
31
|
}
|
30
32
|
|
31
33
|
#offCanvas {
|
32
|
-
color:
|
33
|
-
background: #
|
34
|
+
color: #CECECE;
|
35
|
+
background: #BD000D;
|
34
36
|
border-right: none;
|
35
37
|
box-shadow: none;
|
36
38
|
padding: 0.5rem;
|
37
39
|
}
|
38
40
|
#offCanvas a {
|
39
|
-
color: #
|
41
|
+
color: #FFFFFF;
|
40
42
|
}
|
41
43
|
|
42
44
|
.contents-button {
|
@@ -341,7 +343,7 @@
|
|
341
343
|
<%= report[:title] %>
|
342
344
|
</h2>
|
343
345
|
</div>
|
344
|
-
|
346
|
+
<%= render "report_data.html.erb", report: report, index: index %>
|
345
347
|
<% if report[:vega_spec] %>
|
346
348
|
<div id="<%= "plot-#{index}" %>"></div>
|
347
349
|
<script>
|
@@ -351,22 +353,14 @@
|
|
351
353
|
width: "container",
|
352
354
|
description: "<%= report[:title] %>",
|
353
355
|
data: {
|
354
|
-
values:
|
355
|
-
<% report[:rows].each do |row| %>
|
356
|
-
{
|
357
|
-
<% report[:header].each_with_index do |h, i| %>
|
358
|
-
"<%= h %>": <%= (row[i].class == Integer or row[i].class == Float) ? row[i] : "\"#{row[i]}\"" %>,
|
359
|
-
<% end %>
|
360
|
-
},
|
361
|
-
<% end %>
|
362
|
-
]
|
356
|
+
values: data_<%= index %>
|
363
357
|
},
|
364
358
|
});
|
365
359
|
vegaEmbed('#<%= "plot-#{index}"%>', plot_spec_<%= index %>);
|
366
360
|
</script>
|
367
361
|
<% end %>
|
368
362
|
<div class="card-section">
|
369
|
-
<%= render "output_table.html.erb", report %>
|
363
|
+
<%= render "output_table.html.erb", report: report, index: index %>
|
370
364
|
</div>
|
371
365
|
</article>
|
372
366
|
<% end %>
|
@@ -392,9 +386,7 @@
|
|
392
386
|
</section>
|
393
387
|
</div>
|
394
388
|
|
395
|
-
<script type="text/javascript" src="https://code.jquery.com/jquery-3.6.0.min.js"></script>
|
396
389
|
<script type="text/javascript" src="js/vendor/what-input.js"></script>
|
397
|
-
<script type="text/javascript" src="https://cdn.datatables.net/v/zf/dt-1.11.3/datatables.min.js"></script>
|
398
390
|
<script src="https://cdn.jsdelivr.net/npm/vega@5"></script>
|
399
391
|
<script type="text/javascript" src="https://cdn.jsdelivr.net/npm/foundation-sites@6.7.4/dist/js/foundation.min.js" crossorigin="anonymous"></script>
|
400
392
|
<script>
|
data/lib/log_sense/version.rb
CHANGED
data/lib/log_sense.rb
CHANGED
data/log_sense.gemspec
CHANGED
@@ -1,39 +1,38 @@
|
|
1
1
|
require_relative 'lib/log_sense/version'
|
2
2
|
|
3
3
|
Gem::Specification.new do |spec|
|
4
|
-
spec.name =
|
4
|
+
spec.name = 'log_sense'
|
5
5
|
spec.version = LogSense::VERSION
|
6
|
-
spec.authors = [
|
7
|
-
spec.email = [
|
6
|
+
spec.authors = ['Adolfo Fibrillation']
|
7
|
+
spec.email = ['adolfo@shair.tech']
|
8
8
|
|
9
|
-
spec.summary = %q{Generate analytics
|
10
|
-
spec.description = %q{Generate
|
11
|
-
spec.homepage =
|
12
|
-
spec.license =
|
13
|
-
spec.required_ruby_version = Gem::Requirement.new(
|
9
|
+
spec.summary = %q{Generate analytics for Apache and Rails log file.}
|
10
|
+
spec.description = %q{Generate analytics in HTML, txt, and SQLite format for Apache and Rails log files.}
|
11
|
+
spec.homepage = 'https://github.com/shair-tech/log_sense/log_sense'
|
12
|
+
spec.license = 'MIT'
|
13
|
+
spec.required_ruby_version = Gem::Requirement.new('>= 2.6.9')
|
14
14
|
|
15
|
-
spec.metadata[
|
15
|
+
spec.metadata['allowed_push_host'] = 'https://rubygems.org/'
|
16
16
|
|
17
|
-
spec.metadata[
|
18
|
-
spec.metadata[
|
19
|
-
spec.metadata[
|
17
|
+
spec.metadata['homepage_uri'] = spec.homepage
|
18
|
+
spec.metadata['source_code_uri'] = 'https://github.com/shair-tech/log_sense/log_sense'
|
19
|
+
spec.metadata['changelog_uri'] = 'https://github.com/shair-tech/log_sense/blob/main/CHANGELOG.org'
|
20
20
|
|
21
21
|
# Specify which files should be added to the gem when it is released.
|
22
22
|
# The `git ls-files -z` loads the files in the RubyGem that have been added into git.
|
23
23
|
spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
|
24
24
|
`git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
25
25
|
end
|
26
|
-
spec.bindir =
|
26
|
+
spec.bindir = 'exe'
|
27
27
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
28
|
-
spec.require_paths = [
|
28
|
+
spec.require_paths = ['lib']
|
29
29
|
|
30
|
-
spec.add_dependency
|
31
|
-
spec.add_dependency
|
32
|
-
spec.add_dependency
|
33
|
-
spec.add_dependency
|
34
|
-
spec.add_dependency
|
35
|
-
spec.add_dependency "terminal-table"
|
30
|
+
spec.add_dependency 'browser'
|
31
|
+
spec.add_dependency 'ipaddr'
|
32
|
+
spec.add_dependency 'iso_country_codes'
|
33
|
+
spec.add_dependency 'sqlite3'
|
34
|
+
spec.add_dependency 'terminal-table'
|
36
35
|
|
37
36
|
spec.add_development_dependency 'byebug'
|
38
|
-
spec.add_development_dependency
|
37
|
+
spec.add_development_dependency 'minitest'
|
39
38
|
end
|
metadata
CHANGED
@@ -1,29 +1,15 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: log_sense
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.3.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
|
-
- Adolfo
|
7
|
+
- Adolfo Fibrillation
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-01-12 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
|
-
- !ruby/object:Gem::Dependency
|
14
|
-
name: apache_log-parser
|
15
|
-
requirement: !ruby/object:Gem::Requirement
|
16
|
-
requirements:
|
17
|
-
- - ">="
|
18
|
-
- !ruby/object:Gem::Version
|
19
|
-
version: '0'
|
20
|
-
type: :runtime
|
21
|
-
prerelease: false
|
22
|
-
version_requirements: !ruby/object:Gem::Requirement
|
23
|
-
requirements:
|
24
|
-
- - ">="
|
25
|
-
- !ruby/object:Gem::Version
|
26
|
-
version: '0'
|
27
13
|
- !ruby/object:Gem::Dependency
|
28
14
|
name: browser
|
29
15
|
requirement: !ruby/object:Gem::Requirement
|
@@ -122,10 +108,10 @@ dependencies:
|
|
122
108
|
- - ">="
|
123
109
|
- !ruby/object:Gem::Version
|
124
110
|
version: '0'
|
125
|
-
description: Generate
|
126
|
-
|
111
|
+
description: Generate analytics in HTML, txt, and SQLite format for Apache and Rails
|
112
|
+
log files.
|
127
113
|
email:
|
128
|
-
- adolfo
|
114
|
+
- adolfo@shair.tech
|
129
115
|
executables:
|
130
116
|
- log_sense
|
131
117
|
extensions: []
|
@@ -138,12 +124,14 @@ files:
|
|
138
124
|
- LICENSE.txt
|
139
125
|
- README.org
|
140
126
|
- Rakefile
|
127
|
+
- apache-screenshot.png
|
141
128
|
- bin/console
|
142
129
|
- bin/setup
|
143
130
|
- exe/log_sense
|
144
131
|
- ip_locations/dbip-country-lite.sqlite3
|
145
132
|
- lib/log_sense.rb
|
146
133
|
- lib/log_sense/apache_data_cruncher.rb
|
134
|
+
- lib/log_sense/apache_log_line_parser.rb
|
147
135
|
- lib/log_sense/apache_log_parser.rb
|
148
136
|
- lib/log_sense/emitter.rb
|
149
137
|
- lib/log_sense/ip_locator.rb
|
@@ -156,6 +144,7 @@ files:
|
|
156
144
|
- lib/log_sense/templates/_output_table.html.erb
|
157
145
|
- lib/log_sense/templates/_performance.html.erb
|
158
146
|
- lib/log_sense/templates/_performance.txt.erb
|
147
|
+
- lib/log_sense/templates/_report_data.html.erb
|
159
148
|
- lib/log_sense/templates/_summary.html.erb
|
160
149
|
- lib/log_sense/templates/_summary.txt.erb
|
161
150
|
- lib/log_sense/templates/apache.html.erb
|
@@ -166,14 +155,14 @@ files:
|
|
166
155
|
- sample_logs/empty_log.log
|
167
156
|
- sample_logs/safety-critical_org.log
|
168
157
|
- sample_logs/spmbook_com.log
|
169
|
-
homepage: https://
|
158
|
+
homepage: https://github.com/shair-tech/log_sense/log_sense
|
170
159
|
licenses:
|
171
160
|
- MIT
|
172
161
|
metadata:
|
173
162
|
allowed_push_host: https://rubygems.org/
|
174
|
-
homepage_uri: https://
|
175
|
-
source_code_uri: https://
|
176
|
-
changelog_uri: https://
|
163
|
+
homepage_uri: https://github.com/shair-tech/log_sense/log_sense
|
164
|
+
source_code_uri: https://github.com/shair-tech/log_sense/log_sense
|
165
|
+
changelog_uri: https://github.com/shair-tech/log_sense/blob/main/CHANGELOG.org
|
177
166
|
post_install_message:
|
178
167
|
rdoc_options: []
|
179
168
|
require_paths:
|
@@ -182,15 +171,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
182
171
|
requirements:
|
183
172
|
- - ">="
|
184
173
|
- !ruby/object:Gem::Version
|
185
|
-
version: 2.
|
174
|
+
version: 2.6.9
|
186
175
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
187
176
|
requirements:
|
188
177
|
- - ">="
|
189
178
|
- !ruby/object:Gem::Version
|
190
179
|
version: '0'
|
191
180
|
requirements: []
|
192
|
-
rubygems_version: 3.
|
181
|
+
rubygems_version: 3.0.3.1
|
193
182
|
signing_key:
|
194
183
|
specification_version: 4
|
195
|
-
summary: Generate analytics
|
184
|
+
summary: Generate analytics for Apache and Rails log file.
|
196
185
|
test_files: []
|