Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
7817e02
Release automate
GAS85 Feb 12, 2026
2dc4f2a
Update build arguments in docker-release workflow
GAS85 Feb 12, 2026
d1c8e36
Minor update
GAS85 Feb 12, 2026
43b2c33
Clean up Docker tags in docker-release.yml
GAS85 Feb 12, 2026
9130aa5
Temporary disable master
GAS85 Feb 12, 2026
ff58be8
add original repository
GAS85 Feb 12, 2026
1fb61cb
- Add `.dockerignore` to reduce image size
GAS85 Mar 2, 2026
a2d869f
Add `TELNET_RATE`
GAS85 Mar 2, 2026
39e2859
Support existing banners for SSH in Telnet.
GAS85 Mar 2, 2026
d0808c3
Add Dynamic Repo to the tags
GAS85 Mar 5, 2026
87639bb
Repo Name lower Case correction
GAS85 Mar 5, 2026
769b443
Reduce Image size from 300+ MB to 10 MB
GAS85 Mar 5, 2026
69f923c
Merge branch 'release-pipeline'
GAS85 Mar 5, 2026
290d94c
Merge branch 'master' into feat/telnet
GAS85 Mar 5, 2026
c51c0d3
Merge branch 'feat/telnet'
GAS85 Mar 5, 2026
e872c7a
strips basic `IAC <cmd> <opt>` sequences to make logging cleaner
GAS85 Mar 5, 2026
d8ead9c
strips basic `IAC <cmd> <opt>` sequences to make logging cleaner
GAS85 Mar 5, 2026
1651df7
As we moved to Alpine, wget will not work as before
GAS85 Mar 5, 2026
59c430f
Merge branch 'release-pipeline'
GAS85 Mar 5, 2026
3818597
Harmonize logging output
GAS85 Mar 5, 2026
059e1c8
Merge branch 'feat/telnet'
GAS85 Mar 5, 2026
6d16d81
Revise README with Docker and fail2ban details
GAS85 Mar 7, 2026
daa6280
Remove unsupported part of fail2ban
GAS85 Mar 8, 2026
c441176
Rollback all changes to be synced with upstream master
GAS85 May 21, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ LABEL maintainer="Justin Azoff <justin.azoff@gmail.com>" \

ENV USER=nobody
ENV SSHD_BIND=:2222
ENV TELNET_BIND=:2323

WORKDIR /app

Expand All @@ -22,6 +23,6 @@ RUN go install . && \

USER $USER

EXPOSE 2222
EXPOSE 2222 2323

CMD test -f /var/log/ssh-auth-logger.log || { echo 'Creating log file...' && touch /var/log/ssh-auth-logger.log ; }; /go/bin/ssh-auth-logger 2>&1 | tee -a /var/log/ssh-auth-logger.log
74 changes: 67 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ ssh-auth-logger logs all authentication attempts as json making it easy to consu

ssh-auth-logger uses HMAC to hash the destination IP address and a key in order to generate a consistently "random" key for every responding IP address. This means you can run ssh-auth-logger on a /16 and every ip address will appear with a different host key. Random sshd version reporting as well.

## Example log entry
### Example log entry

This is normally logged on one line

Expand Down Expand Up @@ -56,7 +56,7 @@ sudo setcap cap_net_bind_service=+ep ~/go/bin/ssh-auth-logger
Bind to port 2222 in a host machine

```shell
docker run -t -i --rm -p 2222:22 justinazoff/ssh-auth-logger
docker run -t -i --rm -p 2222:2222 justinazoff/ssh-auth-logger
```

Docker compose example:
Expand All @@ -72,22 +72,28 @@ services:
image: justinazoff/ssh-auth-logger:latest
container_name: ssh-auth-logger
environment:
- TZ=Europe/Berlin # You can set Time Zone to see logs with your local time
# Following are default values
# - SSHD_RATE=120 # bits per second, emulate very slow connection
# - SSHD_BIND=:22 # Port and interface to listen
# SSHD Part
# - SSHD_RATE=320 # bits per second, emulate very slow connection
# - SSHD_BIND=:2222 # Port and interface sshd to listen
# - SSHD_KEY_KEY="Take me to your leader" # It's a secret key that is used to generate a deterministic hash value for a given host IP address
# - SSHD_MAX_AUTH_TRIES=6 # The minimum number of authentication attempts allowed
# - SSHD_RSA_BITS=3072 # If you use 'rsa' you can also set RSA key size, 2048, 3072, 4096 (very rare)
# - SSHD_PROFILE_SCOPE=host # Can be 'remote_ip' (each remote IP gets its own profile, simulating per-attacker behavior.), or anything else for 'host' (the same local host always gets the same profile, e.g. binding to 0.0.0.0:22 will always select the same Profile).
# - SSHD_SEND_BANNER=false # Send SSH Login Banner before Password prompt
# - SSHD_LOG_CLEAR_PASSWORD=true # Log Passwords as clear text or Base64 coded
# - SSHD_LOGS_FILTER="" # Comma-separated list of allowed fields. 'msg', 'level' and 'time' can't be removed. Following combinations are possible: "duser,src,spt,dst,dpt,client_version,server_version,password,keytype,fingerprint,server_key_type,destinationServicename,product"
- TZ=Europe/Berlin # You can set Time Zone to see logs with your local time
# Telnet Part
# - TELNET_BIND=:2323 # Port and interface telnetd to listen
# - TELNET_LOG_CLEAR_PASSWORD=true # Log Passwords as clear text or Base64 coded
# - TELNET_RATE=20 # bits per second, emulate very slow connection
volumes:
# Mount log file if needed
- /var/docker/ssh-auth-logger/log:/var/log
ports:
- 2222:22 # SSH Auth Logger
- 2222:2222 # SSH Auth Logger
- 2323:2323 # SSH Auth Logger Telnet
networks:
# Use isolated docker network, so that other containers will be not reachable from it
- isolated_net
Expand All @@ -99,7 +105,7 @@ services:
memory: 100M
healthcheck:
# Will test if port is still open AND log file was not vanished by host machine log rotate
test: wget -v localhost$$SSHD_BIND --no-verbose --tries=1 --spider && test -s /var/log/ssh-auth-logger.log || exit 1
test: pgrep ssh-auth-logger && test -s /var/log/ssh-auth-logger.log || exit 1
interval: 5m00s
timeout: 5s
retries: 2
Expand All @@ -109,3 +115,57 @@ services:
options:
max-size: 10m
```

## fail2ban configuration

To configure [fail2ban](https://github.com/fail2ban/fail2ban) you have to create a filter:

```shell
sudo nano /etc/fail2ban/filter.d/ssh-auth-logger.local
```

with following content:

```shell
[Definition]
_daemon = ssh-auth-logger

# Match JSON log line with a "time", "msg" fields and a "src" IP
failregex = ^.*"msg":"Request with (password|key)".*"src":"<HOST>".*$
^.*"msg":"Telnet login attempt".*"src":"<HOST>".*$

datepattern = %%Y-%%m-%%dT%%H:%%M:%%S(?:Z|%%z)

ignoreregex =
```

The you have to update your `jail.local`:

```shell
sudo nano /etc/fail2ban/jail.local
```

with following config:

```shell
[ssh-auth-honeypot]
enabled = true
filter = ssh-auth-logger
action = iptables-allports
# Additonally you can setup abuseipdb reporting as per https://github.com/fail2ban/fail2ban/blob/master/config/action.d/abuseipdb.conf
#abuseipdb[abuseipdb_category="18,22"]
# Docker mount log to the localsystem
logpath = /var/docker/ssh-auth-logger/log/ssh-auth-logger.log
# maxretry should be equal or more than in a SSHD_MAX_AUTH_TRIES
maxretry = 6
# For very slow attacker that tries 3 passwords per day
findtime = 1d
# Ban time can be anything you like
bantime = 1d
```

After that you have to reload your fail2ban with command:

```shell
sudo fail2ban-client reload
```
Loading