Skip to content

Commit

Permalink
Merge pull request #52 from idealista/develop
Browse files Browse the repository at this point in the history
Develop
  • Loading branch information
jmonterrubio authored Feb 28, 2018
2 parents e5d1d22 + a5b5c11 commit b70509e
Show file tree
Hide file tree
Showing 57 changed files with 827 additions and 358 deletions.
8 changes: 8 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,14 @@ celerybeat-schedule
env/
venv/
ENV/
.env.leave

#Pycharm stuff
*.settings
*.project
*.classpath
*.idea
*.iml

# Spyder project settings
.spyderproject
Expand Down
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,12 @@ This project adheres to [Semantic Versioning](http://semver.org/) and [Keep a ch

## [Unreleased](https://github.com/idealista/prom2teams/tree/develop)

## [2.0.0](https://github.com/idealista/prom2teams/tree/2.0.0)
[Full Changelog](https://github.com/idealista/prom2teams/compare/1.3.0...2.0.0)
### Added
- *[#49](https://github.com/idealista/prom2teams/issues/49) Update service startup for production environment* @jmonterrubio
- *[#22](https://github.com/idealista/prom2teams/issues/22) Allow to configure multiple connectors* @manuhortet @Gkrlo

## [1.3.0](https://github.com/idealista/prom2teams/tree/1.3.0)
[Full Changelog](https://github.com/idealista/prom2teams/compare/1.2.0...1.3.0)
### Added
Expand Down
6 changes: 2 additions & 4 deletions MANIFEST.in
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
include README.md
include LICENSE
include requirements.txt
include config.ini
include logging_console_config.ini
include logging_file_config.ini
include prom2teams/teams/template.j2
include */config/*
recursive-include */resources/ *
79 changes: 67 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,10 @@

<img src="assets/example.png" alt="Alert example" style="width: 600px;"/>

**prom2teams** is an HTTP server built with Python that receives alert notifications from a previously configured [Prometheus Alertmanager](https://github.com/prometheus/alertmanager) instance and forwards it to [Microsoft Teams](https://teams.microsoft.com/) using defined connectors.
**prom2teams** is a Web server built with Python that receives alert notifications from a previously configured [Prometheus Alertmanager](https://github.com/prometheus/alertmanager) instance and forwards it to [Microsoft Teams](https://teams.microsoft.com/) using defined connectors.

- [Getting Started](#getting-started)
- [Prerequisities](#prerequisities)
- [Prerequisities](#prerequisites)
- [Installing](#installing)
- [Usage](#usage)
- [Config file](#config-file)
Expand Down Expand Up @@ -42,27 +42,70 @@ $ pip3 install prom2teams

## Usage

**Important:** Config path must be provided with at least one Microsoft Teams Connector. Check the options to know how you can supply it.

```bash
# To start the server (a config file path must be provided, log file path, log level and Jinja2 template path are optional arguments):
$ prom2teams --configpath <config file path> [--logfilepath <log file path>] [--loglevel (DEBUG|INFO|WARNING|ERROR|CRITICAL)] [--templatepath <Jinja2 template file path>]
# To start the server (config file path , log file path, log level and Jinja2 template path are optional arguments):
$ prom2teams [--configpath <config file path>] [--logfilepath <log file path>] [--loglevel (DEBUG|INFO|WARNING|ERROR|CRITICAL)] [--templatepath <Jinja2 template file path>]

# To show the help message:
$ prom2teams --help
```

**Note:** default log level is INFO. Messages are redirected to stdout if no log file path is provided.
Another options to start the service are:

```bash
export APP_CONFIG_FILE=<config file path>
$ prom2teams
```

For production environments you should prefer using a WSGI server. You can launch instead:

```bash
$ prom2teams_uwsgi <path to uwsgi ini config>
```

And uwsgi would look like:

```
[uwsgi]
master = true
processes = 5
#socket = 0.0.0.0:8001
#protocol = http
socket = /tmp/prom2teams.sock
chmod-socket = 660
vacuum = true
env = APP_ENVIRONMENT=pro
env = APP_CONFIG_FILE=/etc/default/prom2teams.ini
```

Consider not provide `chdir` property neither `module` property.

**Note:** default log level is DEBUG. Messages are redirected to stdout. To enable file log, set the env APP_ENVIRONMENT=(pro|pre)


### Config file

The config file is an [INI file](https://docs.python.org/3/library/configparser.html#supported-ini-file-structure) and should have the structure described below:

```
[Microsoft Teams]
# At least one connector is required here
Connector: <webhook url>
AnotherConnector: <webhook url>
...
[HTTP Server]
Host: <host ip> # default: 0.0.0.0
Host: <host ip> # default: localhost
Port: <host port> # default: 8089
[Microsoft Teams]
Connector: <webhook url> # required value
[Log]
Level: <loglevel (DEBUG|INFO|WARNING|ERROR|CRITICAL)> # default: DEBUG
Path: <log file path> # default: /var/log/prom2teams/prom2teams.log
[Template]
Path: <Jinja2 template path> # default: app resources template
```

### Configuring Prometheus
Expand All @@ -71,26 +114,38 @@ The [webhook receiver](https://prometheus.io/docs/alerting/configuration/#<webho

The url is formed by the host and port defined in the previous step.

**Note:** In order to keep compatibility with previous versions, v2.0 keep attending the default connector ("Connector") in the endpoint 0.0.0.0:8089. This will be removed in future versions.

```
# The prom2teams endpoint to send HTTP POST requests to.
url: 0.0.0.0:8089
// The prom2teams endpoint to send HTTP POST requests to.
url: 0.0.0.0:8089/v2/<Connector1>
```

### Templating

prom2teams provides a [default template](app/teams/template.j2) built with [Jinja2](http://jinja.pocoo.org/docs/2.9/) to render messages in Microsoft Teams. This template could be overrided using the 'templatepath' argument ('--templatepath <Jinja2 template file path>') during the application start.
prom2teams provides a [default template](prom2teams/resources/templates/teams.j2) built with [Jinja2](http://jinja.pocoo.org/docs/2.10/) to render messages in Microsoft Teams. This template could be overrided using the 'templatepath' argument ('--templatepath <Jinja2 template file path>') during the application start.

Some fields are considered mandatory when received from Alert Manager.
If such a field is not included a default value of 'unknown' is assigned as described below:

Other optional fields are skipped and not included in the Teams message.

#### Swagger UI

Accessing to `<Host>:<Port>` (e.g. `localhost:8001`) in a web browser shows the API v1 documentation.

<img src="assets/swagger_v1.png" alt="Swagger UI" style="width: 600px;"/>

Accessing to `<Host>:<Port>/v2` (e.g. `localhost:8001/v2`) in a web browser shows the API v2 documentation.

<img src="assets/swagger_v2.png" alt="Swagger UI" style="width: 600px;"/>

## Testing

To run the test suite you should type the following:

```bash
# After cloning prom2teams :)
// After cloning prom2teams :)
$ python3 -m unittest discover tests
```

Expand Down
Binary file added assets/swagger_v1.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added assets/swagger_v2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
22 changes: 5 additions & 17 deletions bin/prom2teams
Original file line number Diff line number Diff line change
@@ -1,26 +1,14 @@
#!/usr/bin/env python3

import sys
import os
import argparse


try:
from prom2teams.server import run
from prom2teams.app.api import app as application
except ImportError:
sys.path.append(os.path.abspath('./'))
from prom2teams.server import run
from prom2teams.app.api import app as application

if __name__ == "__main__":
parser = argparse.ArgumentParser(description='Receives alert notifications '
'from Prometheus Alertmanager '
'(https://github.com/prometheus/alertmanager) '
'and sends it to Microsoft Teams using configured connectors ')

parser.add_argument('-c', '--configpath', help='config INI file path', required=True)
parser.add_argument('-l', '--logfilepath', help='log file path', required=False)
parser.add_argument('-v', '--loglevel', help='log level', required=False, default='INFO')
parser.add_argument('-t', '--templatepath', help='Jinja2 template file path', required=False)

args = parser.parse_args()

run(args.configpath, args.templatepath, args.logfilepath, args.loglevel)
_host, _port = application.config['SERVER_NAME'].split(':', 1)
application.run(host=_host, port=int(_port))
12 changes: 12 additions & 0 deletions bin/prom2teams_uwsgi
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#!/bin/bash

set -e

if [[ -n $1 ]]; then
config=$1
else
echo "Provide a uwsgi ini file (without module and chdir flag)"
exit 1
fi

uwsgi $config --chdir `dirname "$0"` --module wsgi
13 changes: 13 additions & 0 deletions bin/wsgi.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import sys
import os


try:
from prom2teams.app.api import app as application
except ImportError:
sys.path.append(os.path.abspath('./'))
from prom2teams.app.api import app as application


if __name__ == "__main__":
application.run()
17 changes: 17 additions & 0 deletions dockerhub/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
FROM python:3.5-slim-jessie

LABEL maintainer="[email protected]"

EXPOSE 8089

RUN pip install prom2teams
COPY config.ini /opt/prom2teams/config.ini
COPY prom2teams_start.sh /opt/prom2teams/prom2teams_start.sh
COPY replace_config.py /opt/prom2teams/replace_config.py

ENV PROM2TEAMS_PORT="8089"
ENV PROM2TEAMS_HOST="0.0.0.0"
ENV PROM2TEAMS_LOGLEVEL="INFO"
ENV PROM2TEAMS_CONNECTOR=""

ENTRYPOINT ["bash", "/opt/prom2teams/prom2teams_start.sh"]
6 changes: 6 additions & 0 deletions dockerhub/config.ini
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
[HTTP Server]
Host: prom2teamshost
Port: prom2teamsport

[Microsoft Teams]
Connector: prom2teamsconnector
3 changes: 3 additions & 0 deletions dockerhub/prom2teams_start.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
#!/bin/bash
python /opt/prom2teams/replace_config.py
prom2teams --configpath /opt/prom2teams/config.ini --loglevel $PROM2TEAMS_LOGLEVEL
12 changes: 12 additions & 0 deletions dockerhub/replace_config.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#!/usr/bin/env python
import os

with open('/opt/prom2teams/config.ini', 'r') as file:
filedata = file.read()

filedata = filedata.replace("prom2teamsport", os.environ.get("PROM2TEAMS_PORT"))
filedata = filedata.replace("prom2teamshost", os.environ.get("PROM2TEAMS_HOST"))
filedata = filedata.replace("prom2teamsconnector", os.environ.get("PROM2TEAMS_CONNECTOR"))

with open('/opt/prom2teams/config.ini', 'w') as file:
file.write(filedata)
3 changes: 3 additions & 0 deletions prom2teams/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
import os

root = os.path.abspath(os.path.dirname(__file__))
File renamed without changes.
33 changes: 33 additions & 0 deletions prom2teams/app/api.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import logging.config

from flask import Flask, Blueprint

from prom2teams.app.configuration import config_app, setup_logging
from .versions.v1 import api_v1
from .versions.v1.namespace import ns as ns_v1
from .versions.v2 import api_v2
from .versions.v2.namespace import ns as ns_v2

log = logging.getLogger('prom2teams_app')

app = Flask(__name__)


def register_api(application, api, namespace, blueprint):
api.init_app(blueprint)
api.add_namespace(namespace)
application.register_blueprint(blueprint)


def init_app(application):
config_app(application)
setup_logging(application)

blueprint_v1 = Blueprint('api_v1', __name__, url_prefix=application.config['API_V1_URL_PREFIX'])
blueprint_v2 = Blueprint('api_v2', __name__, url_prefix=application.config['API_V2_URL_PREFIX'])
register_api(application, api_v1, ns_v1, blueprint_v1)
register_api(application, api_v2, ns_v2, blueprint_v2)


init_app(app)
log.info(app.config['APP_NAME'] + ' started on ' + app.config['SERVER_NAME'])
Loading

0 comments on commit b70509e

Please sign in to comment.