Home

Awesome

surfacescan

Attack surface scanner

Run local

Prerequisites

Docker way

Build images

foo@bar:~$ docker-compose build

Run api

foo@bar:~$ docker-compose up -d api

Run lint (flake8)

foo@bar:~$ docker-compose run --rm lint

Run tests (pytest)

foo@bar:~$ docker-compose run --rm tests

To run locust execute

foo@bar:~$ docker-compose up -d locust

Open in the browser http://localhost:8089 and specify http://api:8001 as host to be tested.

Non docker way

Install dependencies

foo@bar:~$ poetry install

Run flake8

foo@bar:~$ flake8

Run tests

foo@bar:~$ pytest

Start service

foo@bar:~$ uvicorn surfacescan.main:app --reload --port 8001

Notes

Project structure

A service with 2 simple endpoints could be implemented in a single file but one of major goals of this project is to show our approach for structuring a service application.

surfacescan.main

Application initialization, entry point.

surfacescan.api

Routes, HTTP handlers definition. We tried to keep the approach when a HTTP handler is only responsible for "HTTP related staff" and relies on "business logic" modules to do the main work.

surfacescan.registry

As the statistics is bound to the process lifetime we keep it in memory as a single instance. Obviously the environment data should be kept in memory to avoid reading it on each request. So we created a separate module which is resposible for "instantiating" dependencies required by request handlers.

surfacescan.tracking

Module responsible for statistics accumulation. The middleware just uses the tracking function provided so we can easily change the implementation (for example send data to statsd) and do not touch the middleware itself.

surfacescan.scanning

Module responsible for scanning the attack surface. Test cases described in tests/data_scanning.py illustrate our understanding (or its lack) of the problem.

gendata.py

Allows to generate big (or actually any sizes which can fit memory available) data sets for performance testing purposes.

What would be nice to have but is not implemented due to time restrictions