mirror of
https://github.com/zeek/zeek.git
synced 2025-10-02 06:38:20 +00:00

This is based on commit 2731def9159247e6da8a3191783c89683363689c from the zeek-docs repo.
407 lines
12 KiB
ReStructuredText
407 lines
12 KiB
ReStructuredText
.. _ZeekControl documentation: https://github.com/zeek/zeekctl
|
||
.. _FAQ: https://zeek.org/faq/
|
||
.. _Get Zeek: https://zeek.org/get-zeek/
|
||
.. _Zeek source code: https://github.com/zeek/zeek
|
||
.. _gzip: https://www.gzip.org/
|
||
|
||
.. _quickstart:
|
||
|
||
=================
|
||
Quick Start Guide
|
||
=================
|
||
|
||
Zeek is a network traffic analyzer. Zeek works on most modern Unix-based
|
||
systems and does not require custom hardware. See :doc:`install` in order to
|
||
install from pre-built binary packages, or :doc:`building-from-source` in order
|
||
to build Zeek from source.
|
||
|
||
We will first analyze previously captured network traffic from a ``pcap`` file -
|
||
:download:`quickstart.pcap <traces/quickstart.pcap>`. Later, we will use Zeek to
|
||
monitor live traffic. Each section builds on the previous section.
|
||
|
||
Running Zeek
|
||
============
|
||
|
||
Open a terminal, navigate to a clean directory, and run zeek on the
|
||
:file:`quickstart.pcap` file:
|
||
|
||
.. code-block:: console
|
||
|
||
zeek -r quickstart.pcap LogAscii::use_json=T
|
||
|
||
Zeek should not produce any output, but it will create a few log files:
|
||
|
||
* :file:`conn.log`
|
||
* :file:`http.log`
|
||
* :file:`weird.log`
|
||
|
||
The connection log, or :file:`conn.log`, records each connection that Zeek
|
||
detects. The created :file:`conn.log` has two entries. Here are those entries
|
||
(some fields are cut for brevity with "..."):
|
||
|
||
.. code-block:: console
|
||
|
||
|
||
{
|
||
"ts": 1747147647.668533,
|
||
"uid": "CmgO6f3ddanrRjiCoc",
|
||
...
|
||
},
|
||
{
|
||
"ts": 1747147654.27566,
|
||
"uid": "CQuwSY2FD0NsLn9CJj",
|
||
...
|
||
}
|
||
|
||
Now to find out more about both of these connections. Looking at the HTTP log,
|
||
it also has two entries. Take note of the ``uid`` field, short for unique
|
||
identifier. You can use that field to pivot from :file:`conn.log` to
|
||
:file:`http.log` - the UIDs in one should correlate to entries in the other. The
|
||
abbreviated logs for these two requests are:
|
||
|
||
.. code-block:: console
|
||
|
||
{
|
||
"ts": 1747147647.702181,
|
||
"uid": "CmgO6f3ddanrRjiCoc",
|
||
"method": "GET",
|
||
"host": "zeek.org",
|
||
"uri": "/",
|
||
...
|
||
},
|
||
{
|
||
"ts": 1747147654.311012,
|
||
"uid": "CQuwSY2FD0NsLn9CJj",
|
||
"method": "WEIRD",
|
||
"host": "zeek.org",
|
||
"uri": "/",
|
||
...
|
||
}
|
||
|
||
The first entry is a simple ``GET`` request to zeek.org. The second entry used
|
||
a non-standard HTTP method: ``WEIRD``. Zeek also records unusual or unexpected
|
||
behavior in :file:`weird.log`, such as this invalid HTTP method. Now, pivot
|
||
from :file:`http.log` to :file:`weird.log`, where there will be a "weird" for
|
||
the second entry's UID:
|
||
|
||
.. code-block:: console
|
||
|
||
{
|
||
"ts": 1747147654.311012,
|
||
"uid": "CQuwSY2FD0NsLn9CJj",
|
||
"name": "unknown_HTTP_method",
|
||
"addl": "WEIRD",
|
||
...
|
||
}
|
||
|
||
The UID for this entry is the same as the second entry in :file:`conn.log` and
|
||
:file:`http.log`. Therefore, there were two HTTP requests, one with a ``GET``
|
||
request and one with a ``WEIRD`` request. The ``WEIRD`` request was rightfully
|
||
classified as a "weird" by Zeek.
|
||
|
||
More information on the various logs and what they report can be found in the
|
||
:doc:`logs/index` section. More information on working with logs can be found in
|
||
the :doc:`log-formats` section.
|
||
|
||
|
||
.. note::
|
||
|
||
This section used ``LogAscii::use_json=T`` in the Zeek invocation, which
|
||
outputs JSON format logs. The remaining invocations in this guide will not
|
||
provide that argument, so Zeek will output tab-separated (TSV) logs. You may
|
||
add ``LogAscii::use_json=T`` to future Zeek invocations if you want JSON
|
||
format logs.
|
||
|
||
Live Traffic
|
||
============
|
||
|
||
Zeek is often used to monitor live network traffic, not just previously captured
|
||
traffic. You can provide Zeek with a network interface to monitor traffic. Any
|
||
traffic on that interface will be analyzed in order to create logs. For example,
|
||
you may run Zeek on the ``en0`` network device (change ``en0`` to the device you
|
||
want to monitor traffic on):
|
||
|
||
.. code-block:: console
|
||
|
||
$ zeek -i en0 -C
|
||
|
||
Root access is typically required to run commands which monitor a network
|
||
device.
|
||
|
||
In another terminal, create the same two HTTP requests we saw earlier via
|
||
``curl``:
|
||
|
||
.. code-block:: console
|
||
|
||
$ curl -X GET http://zeek.org
|
||
$ curl -X WEIRD http://zeek.org
|
||
|
||
Return to the terminal running Zeek and use Ctrl+C to exit. The logs may have
|
||
more than just the two entries found before since Zeek will analyze all traffic
|
||
on that network device. Entries should still appear in :file:`conn.log`,
|
||
:file:`http.log`, and :file:`weird.log` for these commands.
|
||
|
||
.. note::
|
||
|
||
The ``zeek`` invocation above adds a ``-C`` flag. By default, Zeek discards
|
||
network packets with checksum errors. This flag tells Zeek to ignore
|
||
checksums. Modern operating systems and network devices use checksum
|
||
offloading, which leaves the checksums uninitialized. Since Zeek discards
|
||
packets with checksum errors, checksum offloading necessitates the ``-C``
|
||
flag for local network monitoring via Zeek.
|
||
|
||
Scripting
|
||
=========
|
||
|
||
You can also use Zeek's own scripting language in order to modify and extend
|
||
its behavior:
|
||
|
||
.. code-block:: zeek
|
||
|
||
# example.zeek
|
||
event http_request(c: connection, method: string, original_URI: string,
|
||
unescaped_URI: string, version: string)
|
||
{
|
||
print fmt("HTTP request: %s %s (%s->%s)", method, original_URI, c$id$orig_h,
|
||
c$id$resp_h);
|
||
}
|
||
|
||
This script defines an event handler that will run whenever Zeek sees an HTTP
|
||
request. You can run it through Zeek with the data from the pcap you used
|
||
earlier:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zeek example.zeek -r quickstart.pcap
|
||
HTTP request: GET / (192.168.1.8->192.0.78.212)
|
||
HTTP request: WEIRD / (192.168.1.8->192.0.78.212)
|
||
|
||
Or on live traffic:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zeek example.zeek -i en0 -C
|
||
|
||
In another terminal, run the two ``curl`` commands from before:
|
||
|
||
.. code-block:: console
|
||
|
||
$ curl -X GET http://zeek.org
|
||
$ curl -X WEIRD http://zeek.org
|
||
|
||
The terminal running Zeek will print each command as it gets processed.
|
||
|
||
More information on how to use Zeek’s scripting language can be found in the
|
||
:doc:`scripting/index` section. Experiment with Zeek scripting at
|
||
`try.zeek.org <https://try.zeek.org>`_.
|
||
|
||
Managing Zeek
|
||
=============
|
||
|
||
Zeek comes packaged with ZeekControl (``zeekctl``) to manage more complex
|
||
deployments.
|
||
|
||
The same network device used in the Zeek command line can be used with
|
||
``zeekctl``. This will go in a configuration file. For the following example,
|
||
``$PREFIX`` will refer to the installation directory. This is likely
|
||
``/usr/local/zeek`` if built from source or ``/opt/zeek`` if installed from a
|
||
pre-built package.
|
||
|
||
First, update the configuration’s network interface in
|
||
``$PREFIX/etc/node.cfg``. If the device is ``en0``, that would look like:
|
||
|
||
.. code-block:: console
|
||
|
||
[zeek]
|
||
type=standalone
|
||
host=localhost
|
||
interface=en0
|
||
|
||
You can further configure the ``local.zeek`` script found in
|
||
``$PREFIX/share/zeek/site/local.zeek``. ``zeekctl`` loads this script by
|
||
default. It is not overwritten by Zeek upgrades.
|
||
|
||
Run ``zeekctl`` in order to start an interactive prompt and manage your Zeek
|
||
deployment:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zeekctl
|
||
Hint: Run the zeekctl "deploy" command to get started.
|
||
|
||
Welcome to ZeekControl 2.5.0-76
|
||
|
||
Type "help" for help.
|
||
|
||
[ZeekControl] >
|
||
|
||
Then run ``deploy`` to get started:
|
||
|
||
.. code-block:: console
|
||
|
||
[ZeekControl] > deploy
|
||
|
||
In another terminal, run the same two curl commands from before:
|
||
|
||
.. code-block:: console
|
||
|
||
$ curl -X GET http://zeek.org
|
||
$ curl -X WEIRD http://zeek.org
|
||
|
||
Then return to the ZeekControl prompt and stop it:
|
||
|
||
.. code-block:: console
|
||
|
||
[ZeekControl] > stop
|
||
stopping zeek ...
|
||
|
||
And exit from ``zeekctl``:
|
||
|
||
.. code-block:: console
|
||
|
||
[ZeekControl] > exit
|
||
|
||
The logs from ZeekControl will not appear in your current directory. Instead,
|
||
they will appear in ``$PREFIX/logs/current`` when running. Since the process was
|
||
stopped, they will appear in a directory with the current date within
|
||
``$PREFIX/logs/`` - such as ``$PREFIX/logs/2025-01-01/``.
|
||
|
||
These logs are compressed as ``.log.gz`` files from gzip_. You may decompress
|
||
these via ``gunzip`` then read them, or use gzip’s packaged ``zcat`` command.
|
||
On Mac, this looks like:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zcat < $PREFIX/logs/2025-01-08/weird.11:03:38-11:03:43.log.gz
|
||
<...>
|
||
1736352218.157077 CFvENWVlkwVHhLL35 2603:6081:18f0:99e0:7da2:6b81:9a83:cb4e 57823 2606:2800:21f:cb07:6820:80da:af6b:8b2c 80 unknown_HTTP_method WEIRD F zeek -
|
||
|
||
The logs contain the ``WEIRD`` HTTP request.
|
||
|
||
More information on using ZeekControl can be found in the
|
||
`ZeekControl documentation`_. More information on setting up a cluster can be
|
||
found in the :doc:`cluster-setup` section.
|
||
|
||
Clusters
|
||
========
|
||
|
||
ZeekControl is also used to manage a cluster of Zeek processes. A cluster
|
||
contains many processes which analyze traffic together. For this example, all
|
||
nodes will be local, but they may also be split among multiple hosts.
|
||
|
||
First, return to the ``$PREFIX/etc/node.cfg`` configuration file. It currently
|
||
contains one "standalone" node:
|
||
|
||
.. code-block:: console
|
||
|
||
[zeek]
|
||
type=standalone
|
||
host=localhost
|
||
interface=en0
|
||
|
||
|
||
A standalone node is not in a cluster. Instead, this will change to multiple
|
||
nodes which work together. The following configuration is commented out in the
|
||
``node.cfg`` file by default. Remove the ``[zeek]`` node from above and paste
|
||
this into the file:
|
||
|
||
.. code-block:: console
|
||
|
||
[logger]
|
||
type=logger
|
||
host=localhost
|
||
|
||
[manager]
|
||
type=manager
|
||
host=localhost
|
||
|
||
[proxy]
|
||
type=proxy
|
||
host=localhost
|
||
|
||
[worker]
|
||
type=worker
|
||
host=localhost
|
||
interface=en0
|
||
|
||
Now start ``zeekctl`` again with the ``zeekctl`` console command and run it
|
||
with ``deploy``:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zeekctl
|
||
Hint: Run the zeekctl "deploy" command to get started.
|
||
|
||
Welcome to ZeekControl 2.5.0-76
|
||
|
||
Type "help" for help.
|
||
|
||
[ZeekControl] > deploy
|
||
|
||
Now check the status of the cluster with the ``top`` command:
|
||
|
||
.. code-block:: console
|
||
|
||
[ZeekControl] > top
|
||
|
||
Name Type Host Pid VSize Rss Cpu Cmd
|
||
logger logger localhost XXXX 83M 83M 0% zeek
|
||
manager manager localhost XXXX 82M 82M 0% zeek
|
||
proxy proxy localhost XXXX 82M 82M 0% zeek
|
||
worker worker localhost XXXX 84M 84M 0% zeek
|
||
|
||
This is how you can easily check the status of the running cluster. As before,
|
||
run the two ``curl`` commands in another terminal:
|
||
|
||
.. code-block:: console
|
||
|
||
$ curl -X GET http://zeek.org
|
||
$ curl -X WEIRD http://zeek.org
|
||
|
||
Then interrupt the ``top`` command with Ctrl+C and stop the cluster:
|
||
|
||
.. code-block:: console
|
||
|
||
[ZeekControl] > stop
|
||
stopping workers ...
|
||
stopping proxy ...
|
||
stopping manager ...
|
||
stopping logger ...
|
||
[ZeekControl] > exit
|
||
|
||
As before, the logs will be in the ``$PREFIX/logs/`` directory. Check for the
|
||
weird the same way as before:
|
||
|
||
.. code-block:: console
|
||
|
||
$ zcat < $PREFIX/logs/2025-05-14/weird.08:58:26-08:58:31.log.gz
|
||
<...>
|
||
1747227503.828889 C3aXMM2AC3jzZbKl6i 192.168.1.8 60818 192.0.78.150 80 unknown_HTTP_method WEIRD F worker -
|
||
|
||
Users can distribute work across multiple processes or machines with clusters.
|
||
See the `ZeekControl documentation`_ for more information on managing clusters
|
||
and :doc:`cluster-setup` for more information on cluster setup.
|
||
|
||
Next Steps
|
||
==========
|
||
|
||
By this point, we’ve built up from Zeek's simplest use case to clusters.
|
||
Each section has links to guide further discovery. Here are some extra
|
||
considerations:
|
||
|
||
* Follow the interactive Zeek tutorial at
|
||
`try.zeek.org <https://try.zeek.org>`_.
|
||
* Read more of the documentation: the documentation can be read sequentially.
|
||
Documentation for Zeek's out-of-the-box logs can be found in the
|
||
:doc:`logs/index` section.
|
||
* Browse scripts from :samp:`{$PREFIX}/share/zeek/policy` that may be useful to
|
||
load. Their documentation is found in the
|
||
:ref:`overview of script packages <script-packages>`.
|
||
* Review the FAQ_.
|
||
* Join the Zeek community :slacklink:`Slack workspace <>` or
|
||
:discourselink:`forum <>` to interact with fellow Zeekers and Zeek core
|
||
developers.
|
||
* Track Zeek code releases on the `Get Zeek`_ page. Find the release notes
|
||
under each release. These release notes reference the :file:`NEWS` file found
|
||
in the `Zeek source code`_. The :file:`CHANGES` file gives a more granular
|
||
view of each change.
|