Code Monkey home page Code Monkey logo

ssh-log-to-influx's Introduction

Visualize bruteforce SSH attacker's location in real time

Build, test and deploy Docker Image Size Docker Pulls

Multiarch supported linux/amd64,linux/arm/v7,linux/arm64 for Raspberry Pis ๐Ÿ˜„

Thanks to Schkn for its original post https://devconnected.com/geolocating-ssh-hackers-in-real-time/

Preview

Dashboard

Grafana dashboard id : 12323

docker run -e INFLUX_HOST=myinfluxdb.com -e INFLUX_DB=geoloc -p 7070:7070 acouvreur/ssh-log-to-influx

Prerequisites

  • Docker
  • Rsyslog
  • An InfluxDB instance (or use docker-compose.standalone.yml)
  • A Grafana instance (or use docker-compose.standalone.yml)

Getting started

With a bundled InfluxDB and Grafana

docker-compose -f docker-compose.standalone.yml up

With an external InfluxDB

  • INFLUX_PROTOCOL optional default: http Protocol to use, http or https.
  • INFLUX_HOST Influx (FQDN) host to connect to.
  • INFLUX_PORT optional default: 8086 Influx port to connect to.
  • INFLUX_USER optional default: root Username for connecting to the database.
  • INFLUX_PWD optional default: root Password for connecting to the database.
  • INFLUX_DB Database to operate on.

Note: You can use the Docker network FQDN if you put the service in the same Docker network as your InfluxDB instance. INFLUX_HOST will be influx if your service name is influx.

docker-compose up -d

Test the TCP server

  1. docker-compose -f docker-compose.standalone.yml up
  2. netcat localhost 7070 or ncat localhost 7070 with Git bash for Windows
  3. type: Failed password for username from 206.253.167.10 port 11111 ssh2
  4. Data should be parsed and added

Rsyslog configuration

Add this under /etc/rsyslog.conf to forward ssh auth failures to local server :

I have 'PasswordAuthentication' activated

template(name="OnlyMsg" type="string" string="%msg:::drop-last-lf%\n")
if $programname == 'sshd' then {
   if $msg startswith ' Failed' then {
      action(type="omfwd" target="127.0.0.1" port="7070" protocol="tcp" template="OnlyMsg")
   }
}

I have 'PubkeyAuthentication' activated

template(name="OnlyMsg" type="string" string="%msg:::drop-last-lf%\n")
if $programname == 'sshd' then {
   if $msg startswith ' Invalid' then {
      action(type="omfwd" target="127.0.0.1" port="7070" protocol="tcp" template="OnlyMsg")
   } else if $msg startswith ' Disconnected from authenticating' then {
      action(type="omfwd" target="127.0.0.1" port="7070" protocol="tcp" template="OnlyMsg")
   }
}

Debug configuration

  • If you want to skip certificate validation, set NODE_TLS_REJECT_UNAUTHORIZED to 0, but don't do this without understanding the implications.
  • DEBUG_LEVEL: level of logging in log4js, default is "info".

ssh-log-to-influx's People

Contributors

acouvreur avatar dependabot-preview[bot] avatar dependabot[bot] avatar rolfrander avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar

ssh-log-to-influx's Issues

works but with an error

it runs fine but when i did the test using netcat and Failed password for username from 206.253.167.10 port 11111 ssh2 the docker logs show the following error

Failed password for username from 206.253.167.10 port 11111 ssh2
(node:1) UnhandledPromiseRejectionWarning: Error: Internal Server Error
    at once (/app/node_modules/influx/lib/src/pool.js:243:49)
    at ClientRequest.<anonymous> (/app/node_modules/influx/lib/src/pool.js:66:13)
    at Object.onceWrapper (events.js:286:20)
    at ClientRequest.emit (events.js:203:15)
    at HTTPParser.parserOnIncomingClient [as onIncoming] (_http_client.js:565:21)
    at HTTPParser.parserOnHeadersComplete (_http_common.js:111:17)
    at Socket.socketOnData (_http_client.js:451:20)
    at Socket.emit (events.js:198:13)
    at addChunk (_stream_readable.js:288:12)
    at readableAddChunk (_stream_readable.js:269:11)
(node:1) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:1) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.

Rsyslog Filled With Closed Connections

Hello,
First of all, thanks you for the wonderful application you've built. It's awesome seeing just how bad my situation is, now with a nice GUI!
But that's for another time,

I've got it up and running just fine, but my logs are periodically filled with big red,

omfwd: remote server at 127.0.0.1:7070 seems to have closed connection. This often happens when the remote peer (or an interim system like a load balancer or firewall) shuts down or aborts a connection. Rsyslog will re-open the connection if configured to do so (we saw a generic IO Error, which usually goes along with that behaviour). [v8.2102.0 try https://www.rsyslog.com/e/2027 ]

As you can imagine it's pretty obstructive, & I've got not a clue what to do, any ideas?

I've tried opening port 7070 on my firewall, & turning it off to no avail.
I'm running this with docker compose (bundled version) on a Raspberry Pi 3B+, & Nginx.

Is there anything I need to fix, or just turn off logging?

Error in logs 'missing tag value'

Hi, I'm see this error when typing docker-compose logs -f. Some failed login attempts show up in grafana. But a lot of them don't and then this error appears. If you need more information please let me know. Cool project!!

I'm using the docker-compose.standalone.yml file.

version: "3.7"

services:
  ssh-log-to-influx:
    image: acouvreur/ssh-log-to-influx
    build: ./
    restart: always
    environment: 
      - INFLUX_URL=influxdb
      - INFLUX_DB=telegraf
    ports: 
      - 7070:7070/tcp

  #----------------------------------------------#
  # InfluxDB : time series database
  #----------------------------------------------#
  influxdb:
    image: influxdb:latest
    environment: 
      - INFLUXDB_DB=telegraf
      - INFLUXDB_ADMIN_USER=telegraf
      - INFLUXDB_ADMIN_PASSWORD=grafana
    volumes:
      - influxdb_data:/var/lib/influxdb

  #----------------------------------------------#
  # Grafana : analytics and monitoring
  #----------------------------------------------#
  grafana:
    image: "grafana/grafana:master"
    environment: 
      - GF_INSTALL_PLUGINS=grafana-worldmap-panel
    ports: 
      - 3000:3000
    volumes:
      - grafana_data:/var/lib/grafana
      - ./grafana/provisioning:/etc/grafana/provisioning
      - ./grafana/config.ini:/etc/grafana/config.ini
      - ./grafana/dashboards:/var/lib/grafana/dashboards
        
volumes:
  influxdb_data:
  grafana_data:
ssh-log-to-influx_1  | [2020-05-09T13:30:05.272] [INFO] default - CLOSED: ::ffff:172.21.0.1:37480
ssh-log-to-influx_1  | (node:30) UnhandledPromiseRejectionWarning: Error: A 400 Bad Request error occurred: {"error":"unable to parse 'geossh,geohash=wtw2de99s,username=root,port=22010,ip=222.186.175.202,location=Shanghai\\,\\ Shanghai,status=success,country=China,countryCode=CN,region=SH,regionName=Shanghai,city=Shanghai,zip=,timezone=Asia/Shanghai,isp=Chinanet\\ Jiangsu,org=Chinanet\\ JS,as=AS23650\\ AS\\ Number\\ for\\ CHINANET\\ jiangsu\\ province\\ backbone,query=222.186.175.202 value=1': missing tag value"}
ssh-log-to-influx_1  | 
ssh-log-to-influx_1  |     at IncomingMessage.<anonymous> (/app/node_modules/influx/lib/src/pool.js:49:38)
ssh-log-to-influx_1  |     at IncomingMessage.emit (events.js:322:22)
ssh-log-to-influx_1  |     at IncomingMessage.EventEmitter.emit (domain.js:482:12)
ssh-log-to-influx_1  |     at endReadableNT (_stream_readable.js:1187:12)
ssh-log-to-influx_1  |     at processTicksAndRejections (internal/process/task_queues.js:84:21)
ssh-log-to-influx_1  | (node:30) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). To terminate the node process on unhandled promise rejection, use the CLI flag `--unhandled-rejections=strict` (see https://nodejs.org/api/cli.html#cli_unhandled_rejections_mode). (rejection id: 4)```

Please add proper documentation how to setup

I have a running Grafana instance and i added your stuff from your docker-compose.standalone.yml.

However i have no idea how to connect to the influxDB in Grafana, i have tried root:root as credentials and so on but i always get Status 400 back.

I have also no idea if i should use InfluxQL or Flux, or how the datasouce config should look like.

Also your container does not connect to influx:
A 401 Unauthorized error occurred: {"code":"unauthorized","message":"Unauthorized"}

Here are the relevant parts of my compose file:

  grafana:
    image: grafana/grafana
    container_name: grafana
    depends_on:
      - prometheus
      - cadvisor
      - node-exporter
    volumes:
      - grafana-storage:/var/lib/grafana
    env_file:
      - grafana.env
    networks:
      - traefik-network
      - default
    user: "472"
    labels:
      - "traefik.http.routers.grafana.rule=Host(`grafana.domain.io`)"
      - "traefik.http.routers.grafana.service=grafana"
      - "traefik.http.services.grafana.loadbalancer.server.port=3000"
      - "traefik.docker.network=traefik-network"
      - 'traefik.enable=true'
      - 'traefik.http.routers.grafana.entrypoints=https'
      - 'traefik.http.routers.grafana.tls=true'
      - 'traefik.http.routers.grafana.tls.certresolver=le'
      - "traefik.http.routers.grafana.middlewares=chain-authelia@file"
    restart: unless-stopped

  #----------------------------------------------#
  # InfluxDB : time series database
  #----------------------------------------------#
  influxdb:
    image: influxdb:latest
    volumes:
      - ./influxdb:/var/lib/influxdb

  #----------------------------------------------#
  # ssh-log (fail2ban) to influxdb
  #----------------------------------------------#
  ssh-log-to-influx:
    image: acouvreur/ssh-log-to-influx:latest
    restart: unless-stopped
    environment:
      - INFLUX_HOST=influxdb
      - INFLUX_DB=telegraf
#    ports:
#      - 7070:7070/tcp

volumes:
  grafana-storage:
    driver: local
    driver_opts:
      type: none
      o: bind
      device: /data/docker/monitoring/grafana

Syntax

What is the exact syntax for docker-compose.yml? For a configuration of influxdb on another server.

version: "3.7"

services:
  ssh-log-to-influx:
    image: acouvreur/ssh-log-to-influx
    build: ./
    restart: always
    environment:
      - INFLUX_URL=https://mydomain:8086
      - INFLUX_DB=mydb
      - INFLUX_USER=myuser
      - INFLUX_PWD=mystrongpassword
    ports:
      - 7070:7070/tcp

With this configuration the container restarts all the time.

No data

Hi, I installed this repo using docker-compose.standalone.yml and I have rsyslog running and the config you provided.

On my :3000 I had to log in to grafana and from the output of docker I saw that it was authenticating me to router at my home I don't know why? (the IP it used to sent /login is my Modem Router at home) but admin/admin worked and I created a new password.

I found the correct dashboard but it does not have any data. When I try to test Data Sources / InfluxDB with default URL http://influxdb:8086 I get and error database not found: telegraf

Also I am not able to modify the IP of InfluxDB because of this message This datasource was added by config and cannot be modified using the UI. Please contact your server admin to update this datasource.

I'd really appreciate it if you're able to help.

Multiplatform Docker build

As a lot of homelab are raspberry pi based it would be nice to have an ARM build

buildx can do the trick

Does not add line when user is in system but wrong public key/request

When someone tried to brute force and correcty gueses the username but wrong public key it isn't added to the database. This can maby be fixed by adding this code to the /etc/rsyslog.conf for public key.

else if $msg startswith ' Connection reset by authenticating' then {
      action(type="omfwd" target="127.0.0.1" port="7070" protocol="tcp" template="OnlyMsg")
   }

I couldn't quite make up if this was suppored by the acouvreur/ssh-log-to-influx container.

Ram usage so big that Grafana won't load

Hello! ๐Ÿ‘‹

I've been having fun with this for something like a week, and I've noticed that, because I have an insane amount of attack per day (I'm at more than 30k in a few days), the Influx database must have become too big (Haven't checked).

The thing is, because of that, Influx is taking pretty much all my memory on my dedicated server and I'm now unable to access Grafana (I know, I only have 2GB of ram, and if there is no solution I'll unfortunately have to shut it down, but if it's fixable I would love to keep it!)

Influx memory usage

This is the kind of errors I get when I manage to get to Grafana (I also got a 503 from influx one time)
Grafana error

I tried to revert the docker-compose to version "2.4" so I could limit the memory available in the docker-compose but then Grafana wasn't able to retrieve any data from influx...

If I remember correctly, Grafana cannot connect because Influx times-out.

I know it's not really an issue, because I'm pretty sure it's just because I lack of available memory, but I would gladly take any tips for a fix, or else I'm afraid I will have to drop my ssh monitoring ๐Ÿ˜ญ

Exploring other kinds of auth issues

Based on the rsylog config (and I am guessing the parsing code in the container), am I right in thinking that this will only detect the bad password type of error: Failed password for username from 206.253.167.10 port 11111 ssh2

but not these:

May 18 14:09:57 moebius sshd[24830]: Invalid user bob from 72.xx.xx.87 port 38124
May 18 14:09:57 moebius sshd[24830]: input_userauth_request: invalid user bob [preauth]
May 18 14:09:57 moebius sshd[24830]: userauth_pubkey: key type ssh-dss not in PubkeyAcceptedKeyTypes [preauth]
May 18 14:09:57 moebius sshd[24830]: userauth_pubkey: key type ssh-dss not in PubkeyAcceptedKeyTypes [preauth]
May 18 14:09:57 moebius sshd[24830]: Connection closed by 72.xx.xx.87 port 38124 [preauth]
May 18 14:10:09 moebius sshd[24847]: userauth_pubkey: key type ssh-dss not in PubkeyAcceptedKeyTypes [preauth]
May 18 14:10:09 moebius sshd[24847]: userauth_pubkey: key type ssh-dss not in PubkeyAcceptedKeyTypes [preauth]
May 18 14:10:10 moebius sshd[24847]: Connection closed by 72.xx.xx.87 port 38126 [preauth]

That may be more common, since it's best practice to use ssh keys instead of passwords?

Error 400 from Grafana to InfluxDB datasource

Hey guys!
I'm having a bit of a problem with Grafana and InfluxDB. Everything works but I can't get grafana to connect to InfluxDB. It is really weird but I'm getting an Network Error 400.

version: "3.7"

services:
  ssh-log-to-influx:
    image: acouvreur/ssh-log-to-influx:latest
    build: ./
    restart: always
    user: 1000:1000
    environment:
      - INFLUX_HOST=influxdb
      - INFLUX_DB=telegraf
    ports:
      - 7070:7070/tcp
    networks:
      - default

  #----------------------------------------------#
  # InfluxDB : time series database
  #----------------------------------------------#
  influxdb:
    image: influxdb:latest
    user: 1000:1000
    volumes:
      - ./influxdb_data:/var/lib/influxdb
    networks:
      - default
    
  # Grafana : analytics and monitoring
  #----------------------------------------------#
  grafana:
    image: "grafana/grafana:latest"
    user: 1000:1000
    environment:
      - GF_INSTALL_PLUGINS=grafana-worldmap-panel,grafana-piechart-panel
    volumes:
      - ./grafana_data:/var/lib/grafana
      - ./grafana/provisioning:/etc/grafana/provisioning
      - ./grafana/config.ini:/etc/grafana/config.ini
      - ./grafana/dashboards:/var/lib/grafana/dashboards
    networks:
      - default
      - web

networks:
  default:
  web:
    name: web

Any pointers would be really appreaciated!

Add reverse lookup on ip to discover domain names

I recently tried to reverse lookup from attacks.
It gives precious information, and can even lead to discover hacked server based on the domain name without the author knowing it.
I sent an email to an administrator in charge of a small website I found to tell him that his server may be used to send bruteforce attacks.

Read from auth.log file as a stream

Read from the auth.log file as a stream instead of having a TCP server and an RSyslog configuration

The Dockerfile will just need to map on the /var/log/auth.log file as read only.

This is good because in swarm mode it can be extended really easily to monitor all nodes.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.