update elasticsearch/logstash examples so that they work with elastic stack v5
[freeradius.git] / doc / schemas / logstash / logstash-radius.conf
index 8b277a0..a85841a 100644 (file)
@@ -1,7 +1,9 @@
 # logstash configuration to process RADIUS detail files
 #
 # Matthew Newton
-# January 2016
+# January 2017
+#
+# This config has been tested with logstash version 5.1.2.
 # 
 # RADIUS "detail" files are textual representations of the RADIUS
 # packets, and are written to disk by e.g. FreeRADIUS. They look
 
 
 
-# Example input - read data from a file. This can be useful for
-# testing, but usually not so much for live service. For example,
-# to read in a detail file with this input you could use:
+# Example input - read data from a file. For example, to read in a
+# detail file with this input you could use:
+#
+#  # /usr/share/logstash/bin/logstash --path.settings=/etc/logstash -f logstash-radius.conf
 #
-#   /opt/logstash/bin/logstash -v -f logstash-radius.conf < detailfile
 
 input {
-       stdin {
+       file {
+               path => "/path/to/radius/detail/file"
+
+               # Note when testing that logstash will remember where
+               # it got to and continue from there.
+               start_position => "beginning"
+
+               # Set the type, for below.
                type => radiusdetail
+
+               # It is preferable to use a log feeder that can join
+               # multiple lines together, rather than using multiline
+               # here. For an example, see the log-courier
+               # configuration in this directory.
+
+               # If you didn't read the above, go back and read it again.
+
+               # If that is not possible you may be able to use the
+               # following section. Note that if you are using the
+               # "stdin" input, the file is chunked into 16k blobs,
+               # so every 16k a detail record is likely to be chopped
+               # in half. If you are using the "file" input (as in this
+               # example), the blank links between records are not
+               # passed through so the regex here has to be aware of
+               # that. Basically, do multiline as early as possible
+               # in your log feeder client not here and you'll avoid
+               # most issues that are likely to come up.
+
+               codec => multiline {
+                       pattern => "^\t"
+                       negate => false
+                       what => "previous"
+               }
+
+               # If you really want to use the "stdin" input, this
+               # will work better, but be aware of the comments
+               # above.
+
+               #codec => multiline {
+               #       pattern => "^[A-Z\t]"
+               #       negate => false
+               #       what => "next"
+               #}
        }
 }
 
 # Moving into production will likely need something more reliable.
 # There are many input methods, an example here using log-courier
 # (which supports client-site multiline processing and does not
-# lose log events if logstash is restarted).
+# lose log events if logstash is restarted). You could also
+# investigate e.g. filebeat from Elastic.
 
 # input {
 #      courier {
 #              port => 5140
 #              transport => "tcp"
+#
+#              # Don't set the type here, as it's set in the
+#              # log-courier config instead.
+#              #type => radiusdetail
 #      }
 # }
 
@@ -56,22 +104,6 @@ filter {
 
        if [type] == "radiusdetail" {
 
-               # If you are using a log feeder that can join
-               # multiple lines together then that is preferrable
-               # to using multiline here, because this can not be
-               # used with threaded logstash (i.e. -w<n> at
-               # startup).
-
-               # In that case you should comment out the following
-               # section. For example, see the log-courier
-               # configuration configuration in this directory.
-
-               multiline {
-                       pattern => "^[A-Z\t]"
-                       negate => false
-                       what => "next"
-               }
-
                # Pull off the timestamp at the start of the
                # detail record. Note there may be additional data
                # after it that has been added by the local admin,
@@ -92,6 +124,11 @@ filter {
                # This is the bulk of processing that adds all of
                # the RADIUS attributes as elasticsearch fields.
 
+               # Note issue https://github.com/logstash-plugins/logstash-filter-kv/issues/10
+               # currently means that all spaces will be stripped
+               # from all fields. If this is a problem, adjust the
+               # trim setting.
+
                kv {
                        field_split => "\n"
                        source => "message"
@@ -163,14 +200,14 @@ filter {
                # possible to make sure all MAC addresses look the
                # same, which has obvious benefits.
                #
-               # https://github.com/mcnewton/elk/blob/master/logstash-filters/sanitize_mac.rb
+               # https://github.com/mcnewton/logstash-filter-sanitize_mac
 
                # sanitize_mac {
                #       match => {
                #               "Called-Station-Id_mac" => "Called-Station-Id_mac"
                #               "Calling-Station-Id_mac" => "Calling-Station-Id_mac"
                #               }
-               #       separator => ":"
+               #       separator => "-"
                #       fixcase => "lower"
                # }
 
@@ -182,15 +219,15 @@ filter {
 
                if ([Acct-Input-Octets]) {
                        ruby {
-                               code => "event['Acct-Input-Octets_long'] =
-                                       event['Acct-Input-Octets'].to_i + ( event['Acct-Input-Gigawords'] ? (event['Acct-Input-Gigawords'].to_i * (2**32)) : 0)"
+                               code => "event.set('Acct-Input-Octets_long', event.get('Acct-Input-Octets').to_i +
+                                               (event.get('Acct-Input-Gigawords') ? (event.get('Acct-Input-Gigawords').to_i * (2**32)) : 0))"
                        }
                }
 
                if ([Acct-Output-Octets]) {
                        ruby {
-                               code => "event['Acct-Output-Octets_long'] =
-                                       event['Acct-Output-Octets'].to_i + ( event['Acct-Output-Gigawords'] ? (event['Acct-Output-Gigawords'].to_i * (2**32)) : 0)"
+                               code => "event.set('Acct-Output-Octets_long', event.get('Acct-Output-Octets').to_i +
+                                               (event.get('Acct-Output-Gigawords') ? (event.get('Acct-Output-Gigawords').to_i * (2**32)) : 0))"
                        }
                }
 
@@ -199,16 +236,13 @@ filter {
 
 
 
-# Output data to the local elasticsearch cluster (called
-# "elasticsearch") using type "detail" in index "radius-DATE".
+# Output data to the local elasticsearch cluster
+# using type "detail" in index "radius-DATE".
 
 output {
        if [type] == "radiusdetail" {
                elasticsearch {
-                       host => localhost
-                       protocol => http
-                       cluster => elasticsearch
-                       index_type => "detail"
+                       document_type => "detail"
                        index => "radius-%{+YYYY.MM.dd}"
                        flush_size => 1000
                }