Git Product home page Git Product logo

pdh's Introduction

PDH - PagerDuty CLI for humans

Build Image

PDH is a new lightweight CLI for pagerduty interaction: uou can handle your incidents triage without leaving your terminal. It also add some nice tricks to automate the incident triage and easy the on-call burden.

See docs (TBD)

Install

Nix

If you are using cachix you can use the prebuilt packages:

cachix use pdh
nix shell github:mbovo/pdh

Arch linux

yay -S pdh

With docker

docker run -ti -v ~/.config/pdh.yaml:/root/.config/pdh.yaml --rm pdh:0.3.10 inc ls

With pip

pip install pdh>=0.3.10

From source with nix and direnv

git clone https://github.com/mbovo/pdh
direnv allow pdh
cd pdh
pdh inc ls -e

From source with devbox

git clone https://github.com/mbovo/pdh
direnv allow pdh
cd pdh
pdh inc ls -e

From source

git clone https://github.com/mbovo/pdh
cd pdh
task setup
source .venv/bin/activate
pdh inc ls -e

Usage

First of all you need to configure pdh to talk with PagerDuty's APIs:

pdh config

The wizard will prompt you for 3 settings:

  • apikey is the API key, you can generate it from the user's profile page on pagerduty website
  • email the email address of your pagerduty profile
  • uid the userID of your account (you can read it from the browser address bar when clicking on "My Profile")

Settings are persisted to ~/.config/pdh.yaml in clear.

Listing incidents

Assigned to self:

pdh inc ls

Any other incident currently outstanding:

pdh inc ls -e

Auto ACK incoming incidents

Watch for new incidents every 10s and automatically set them to Acknowledged

pdh inc ls --watch --new --ack --timeout 10

List all HIGH priority incidents periodically

List incidents asssigned to all users every 5s

pdh inc ls --high --everything --watch --timeout 5

Resolve specific incidents

pdh inc resolve INCID0001 INCID0024 INCID0023

Resolve all incidents related to Backups

pdh inc ls --resolve --regexp ".*Backup.*"

Rules

PDH support custom scripting applied to your incidents list. These rules are in fact any type of executable you can run on your machine.

pdh inc apply INCID001 -s /path/to/my/script.py -s /path/to/binary

The apply subcommand will call the listed executable/script passing along a json to stdin with the incident informations. The called script can apply any type of checks/sideffects and output another json to stout to answer the call.

Even though rules can be written in any language it's very straightforward using python:

Rules: an example

An example rule can be written in python with the following lines

#!/usr/bin/env python3
from pdh import rules, Filter

@rules.rule
def main(input):
    return {i["id"]: i["summary"] for i in input}

if __name__ == "__main__":
    main()

This is the simplest rule you can write, reading the input and simply output a new dictionary with the entries. It will output something like:

 pdh inc apply Q1LNI5LNM7RZ2C Q1C5KG41H0SZAM -s ./a.py
┏━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓
┃ script ┃ Q1LNI5LNM7RZ2C                                                     ┃ Q1C5KG41H0SZAM                                                                       ┃
┡━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┩
│ ./a.py │  AWS Health Event: us-east-1 EC2 : AWS_EC2_INSTANCE_STOP_SCHEDULED │  AWS Health Event: us-east-1 EC2 : AWS_EC2_INSTANCE_STORE_DRIVE_PERFORMANCE_DEGRADED │
└────────┴────────────────────────────────────────────────────────────────────┴──────────────────────────────────────────────────────────────────────────────────────┘

The default output is table with one line for each script runned and with one column per each element in the returned object

Rules: more examples

#!/usr/bin/env python3

# Needed imports
from pdh import rules, Filter

# This annotation make the main() method parse stdin as json into the parameter called input
# All returned values are converted to json and printed to stdout
@rules.rule
def main(input):

    # Initialize PagerDuty's APIs
    api = rules.api()

    # From the given input extract only incidents with the word cassandra in title
    incs = Filter.objects(input, filters=[Filter.regexp("title", ".*EC2.*")])

    # ackwnoledge all previously filtered incidents
    api.ack(incs)

    # resolve all previously filtered incidents
    api.resolve(incs)

    # snooze all previously filtered incidents for 1h
    api.snooze(incs, duration=3600)

    # Chain a given rule, i.e call that rule with the output of this one
    # chain-loading supports only a single binary, not directories
    c = rules.chain(incs, "rules/test_chaining.sh")

    # Execute an external program and get the output/err/return code
    p: rules.ShellResponse = rules.exec('kubectl get nodes -o name')
    if p.rc > 0:
      nodes = p.stdout.split("\n")

    # if you return a dict will be rendered with each item as a column in a table
    # Othrwise will be converted as string
    return {i["id"]: i["summary"] for i in incs}


if __name__ == "__main__":
    main()

Requirements

Contributing

First of all you need to setup the dev environment, using Taskfile:

task setup

This will create a python virtualenv and install pre-commit and poetry in your system if you lack them.

License

This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. See for more details.

pdh's People

Contributors

dependabot[bot] avatar jsecchiero avatar lorepanichi avatar mbovo avatar

Stargazers

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

Watchers

 avatar  avatar  avatar  avatar

pdh's Issues

Filter basing on service name

As per @davidone-sysdig suggestion we should have something to filter (including and excluding) alerts based on service names (regexp)
Like --exclude-service-regex ".*Debug$" to avoid listing alert coming from debug services

snooze subcommand doesn't work properly

This is what i get trying to snooze an incident ( pdh inc snooze Q0K8O80OC2 )

Traceback (most recent call last):
  File "/Users/manuel.bovo/oss/pdh/.venv/bin/pdh", line 5, in <module>
    main()
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 1128, in __call__
    return self.main(*args, **kwargs)
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 1053, in main
    rv = self.invoke(ctx)
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 1659, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 1659, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 1395, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/core.py", line 754, in invoke
    return __callback(*args, **kwargs)
  File "/Users/manuel.bovo/oss/pdh/.venv/lib/python3.9/site-packages/click/decorators.py", line 26, in new_func
    return f(get_current_context(), *args, **kwargs)
  File "/Users/manuel.bovo/oss/pdh/src/pdh/main.py", line 176, in snooze
    incs = Filter.objects(incs, filters=Filter.inList("id", incidentids))
  File "/Users/manuel.bovo/oss/pdh/src/pdh/filters.py", line 102, in objects
    for filter_func in filters:
TypeError: 'function' object is not iterable

Title with [] are dropped from table output

Any alert title containing some text grouped by square brackets is dropped from the output.

This is mabye due to the rich library interpreting the [ ] characters as formatting

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.