From be2376a4e1da4342fa9cbc96897aa2e77f0460d1 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 11:40:55 +0100 Subject: [PATCH 1/9] add shoutrrr --- docs/notifications.md | 21 +++++++++++++++++++++ go.mod | 1 + go.sum | 19 +++++++++++++++++++ internal/flags/flags.go | 8 +++++++- pkg/notifications/notifier.go | 2 ++ 5 files changed, 50 insertions(+), 1 deletion(-) diff --git a/docs/notifications.md b/docs/notifications.md index b95e95e..6a1a9e9 100644 --- a/docs/notifications.md +++ b/docs/notifications.md @@ -8,6 +8,7 @@ The types of notifications to send are set by passing a comma-separated list of - `slack` to send notifications through a Slack webhook - `msteams` to send notifications via MSTeams webhook - `gotify` to send notifications via Gotify +- `shoutrrr` to send notifications via [containrrr/shoutrrr](https://github.com/containrrr/shoutrrr) > There is currently a [bug](https://github.com/spf13/viper/issues/380) in Viper, which prevents comma-separated slices to be used when using the environment variable. A workaround is available where we instead put quotes around the environment variable value and replace the commas with spaces, as `WATCHTOWER_NOTIFICATIONS="slack msteams"` @@ -115,3 +116,23 @@ docker run -d \ -e WATCHTOWER_NOTIFICATION_GOTIFY_TOKEN="SuperSecretToken" \ containrrr/watchtower ``` + +### [containrrr/shoutrrr](https://github.com/containrrr/shoutrrr) + +To send notifications via shoutrrr, the following command-line options, or their corresponding environment variables, can be set: + +- `--notification-shoutrrr-url` (env. `WATCHTOWER_NOTIFICATION_SHOUTRRR_URL`): The shoutrrr service URL to be used. + +Go to [https://github.com/containrrr/shoutrrr#service-urls](https://github.com/containrrr/shoutrrr#service-urls) to learn more about the different service URLs you can use. + +Example: + +```bash +docker run -d \ + --name watchtower \ + -v /var/run/docker.sock:/var/run/docker.sock \ + -e WATCHTOWER_NOTIFICATIONS=shoutrrr \ + -e WATCHTOWER_NOTIFICATION_SHOUTRRR_URL=discord://channel/token \ + -e WATCHTOWER_NOTIFICATION_SHOUTRRR_URL=slack://watchtower@token-a/token-b/token-c \ + containrrr/watchtower +``` \ No newline at end of file diff --git a/go.mod b/go.mod index 2d2ced6..b6fad27 100644 --- a/go.mod +++ b/go.mod @@ -15,6 +15,7 @@ require ( github.com/cenkalti/backoff v2.2.1+incompatible // indirect github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6 // indirect github.com/containerd/continuity v0.0.0-20181203112020-004b46473808 // indirect + github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752 github.com/docker/cli v0.0.0-20190327152802-57b27434ea29 github.com/docker/distribution v2.7.1+incompatible github.com/docker/docker v0.0.0-20190404075923-dbe4a30928d4 diff --git a/go.sum b/go.sum index 230df62..f83bd71 100644 --- a/go.sum +++ b/go.sum @@ -43,6 +43,8 @@ github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6 h1:A7RURps5t4yDU0 github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6/go.mod h1:yMWuSON2oQp+43nFtAV/uvKQIFpSPerB57DCt9t8sSA= github.com/containerd/continuity v0.0.0-20181203112020-004b46473808 h1:4BX8f882bXEDKfWIf0wa8HRvpnBoPszJJXL+TVbBw4M= github.com/containerd/continuity v0.0.0-20181203112020-004b46473808/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= +github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752 h1:g7iPN6gYedYNetNT7pdSO2jyZWyg9f7OqIVB4wOcEh4= +github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752/go.mod h1:eotQeC9bHbsf9eMUnXOU/y5bskegseWNB4PwmxRO7Wc= github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk= github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= @@ -78,6 +80,8 @@ github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21/go.mod h1 github.com/eapache/queue v1.1.0/go.mod h1:6eCeP0CKFpHLu8blIFXhExK/dRa7WDZfr6jVFPTqq+I= github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 h1:Yzb9+7DPaBjB8zlTR87/ElzFsnQfuHnVUVqpZZIcV5Y= github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0= +github.com/fatih/color v1.7.0 h1:DkWD4oS2D8LGGgTQ6IvwJJXSL5Vp2ffcQg58nFV38Ys= +github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fsnotify/fsnotify v1.4.7 h1:IXs+QLmnXW2CcXuY+8Mzv/fWEsPGWxqefPtCP5CnV9I= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= @@ -108,6 +112,8 @@ github.com/google/certificate-transparency-go v1.0.21 h1:Yf1aXowfZ2nuboBsg7iYGLm github.com/google/certificate-transparency-go v1.0.21/go.mod h1:QeJfpSbVSfYc7RgB3gJFj9cbuQMMchQxrWXz8Ruopmg= github.com/google/go-cmp v0.2.0 h1:+dTQ8DZQJz0Mb/HjFlkptS1FeQ4cWSnN941F8aEG4SQ= github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M= +github.com/google/go-cmp v0.3.0 h1:crn/baboCvb5fXaQ0IJ1SGTsTVrWpDsCWC8EGETZijY= +github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= @@ -130,6 +136,8 @@ github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI= github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU= github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/jarcoal/httpmock v1.0.4 h1:jp+dy/+nonJE4g4xbVtl9QdrUNbn6/3hDT5R4nDIZnA= +github.com/jarcoal/httpmock v1.0.4/go.mod h1:ATjnClrvW/3tijVmpL/va5Z3aAyGvqU3gCT8nX0Txik= github.com/jinzhu/gorm v1.9.11 h1:gaHGvE+UnWGlbWG4Y3FUwY1EcZ5n6S9WtqBA/uySMLE= github.com/jinzhu/gorm v1.9.11/go.mod h1:bu/pK8szGZ2puuErfU0RwyeNdsf3e6nCX/noXaVxkfw= github.com/jinzhu/inflection v1.0.0 h1:K317FqzuhWc8YvSVlFMCCUb36O/S9MCKRDI7QkRKD/E= @@ -161,6 +169,10 @@ github.com/lib/pq v1.2.0 h1:LXpIM/LZ5xGFhOpXAQUIMM1HdyqzVYM13zNdjCEEcA0= github.com/lib/pq v1.2.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/magiconair/properties v1.8.0 h1:LLgXmsheXeRoUOBOjtwPQCWIYqM/LU1ayDtDePerRcY= github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/mattn/go-colorable v0.1.2 h1:/bC9yWikZXAL9uJdulbSfyVNIR3n3trXl+v8+1sx8mU= +github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-isatty v0.0.8 h1:HLtExJ+uU2HOZ+wI0Tt5DtUDrx8yhUqDcp7fYERX4CE= +github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-sqlite3 v1.11.0 h1:LDdKkqtYlom37fkvqs8rMPFKAMe8+SgjbwZ6ex1/A/Q= github.com/mattn/go-sqlite3 v1.11.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc= github.com/matttproud/golang_protobuf_extensions v1.0.1 h1:4hp9jkHxhMHkqkrB3Ix0jegS5sx/RkqARlsWZ6pIwiU= @@ -291,6 +303,7 @@ golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJ golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6 h1:bjcUS9ztw9kFmmIxJInhon/0Is3p+EHBKNgquIzo1OI= golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= @@ -298,6 +311,7 @@ golang.org/x/sys v0.0.0-20181107165924-66b7b1311ac8/go.mod h1:STP8DvDyc/dI5b8T5h golang.org/x/sys v0.0.0-20181116152217-5ac8a444bdc5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190412213103-97732733099d h1:+R4KGOnez64A81RvjARKc4UT5/tI9ujCIVX+P5KiHuI= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg= @@ -313,6 +327,9 @@ golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGm golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= golang.org/x/tools v0.0.0-20190312170243-e65039ee4138/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= +golang.org/x/xerrors v0.0.0-20190513163551-3ee3066db522/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= google.golang.org/api v0.3.1/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMtkk= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0 h1:/wp5JvzpHIxhs/dumFmF7BXTf3Z+dd4uXta4kVyO508= @@ -345,6 +362,8 @@ gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bl gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gosrc.io/xmpp v0.1.1 h1:iMtE9W3fx254+4E6rI34AOPJDqWvpfQR6EYaVMzhJ4s= +gosrc.io/xmpp v0.1.1/go.mod h1:4JgaXzw4MnEv2sGltONtK3GMhj+h9gpQ7cO8nwbFJLU= gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo= gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw= honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= diff --git a/internal/flags/flags.go b/internal/flags/flags.go index a60d18f..4d54f92 100644 --- a/internal/flags/flags.go +++ b/internal/flags/flags.go @@ -121,7 +121,7 @@ func RegisterNotificationFlags(rootCmd *cobra.Command) { "notifications", "n", viper.GetStringSlice("WATCHTOWER_NOTIFICATIONS"), - " notification types to send (valid: email, slack, msteams, gotify)") + " notification types to send (valid: email, slack, msteams, gotify, shoutrrr)") flags.StringP( "notifications-level", @@ -238,6 +238,12 @@ Should only be used for testing. "", viper.GetString("WATCHTOWER_NOTIFICATION_GOTIFY_TOKEN"), "The Gotify Application required to query the Gotify API") + + flags.StringArrayP( + "notification-shoutrrr-url", + "", + viper.GetStringSlice("WATCHTOWER_NOTIFICATION_SHOUTRRR_URL"), + "The shoutrrr URL to send notifications to") } // SetDefaults provides default values for environment variables diff --git a/pkg/notifications/notifier.go b/pkg/notifications/notifier.go index 2f25824..a23a5ee 100644 --- a/pkg/notifications/notifier.go +++ b/pkg/notifications/notifier.go @@ -40,6 +40,8 @@ func NewNotifier(c *cobra.Command) *Notifier { tn = newMsTeamsNotifier(c, acceptedLogLevels) case gotifyType: tn = newGotifyNotifier(c, acceptedLogLevels) + case shoutrrrType: + tn = newShoutrrrNotifier(c, acceptedLogLevels) default: log.Fatalf("Unknown notification type %q", t) } From 2b21bd46bea45a7badb71c7f23ba1d0f10f2d15c Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 13:52:04 +0100 Subject: [PATCH 2/9] add shoutrrr.go --- pkg/notifications/shoutrrr.go | 88 +++++++++++++++++++++++++++++++++++ 1 file changed, 88 insertions(+) create mode 100644 pkg/notifications/shoutrrr.go diff --git a/pkg/notifications/shoutrrr.go b/pkg/notifications/shoutrrr.go new file mode 100644 index 0000000..4c7d2ab --- /dev/null +++ b/pkg/notifications/shoutrrr.go @@ -0,0 +1,88 @@ +package notifications + +import ( + "fmt" + "github.com/containrrr/shoutrrr" + t "github.com/containrrr/watchtower/pkg/types" + log "github.com/sirupsen/logrus" + "github.com/spf13/cobra" +) + +const ( + shoutrrrType = "shoutrrr" +) + +// Implements Notifier, logrus.Hook +type shoutrrrTypeNotifier struct { + Urls []string + entries []*log.Entry + logLevels []log.Level +} + +func newShoutrrrNotifier(c *cobra.Command, acceptedLogLevels []log.Level) t.Notifier { + flags := c.PersistentFlags() + + urls, _ := flags.GetStringArray("notification-shoutrrr-url") + + n := &shoutrrrTypeNotifier{ + Urls: urls, + logLevels: acceptedLogLevels, + } + + log.AddHook(n) + + return n +} + +func (e *shoutrrrTypeNotifier) buildMessage(entries []*log.Entry) string { + body := "" + for _, entry := range entries { + body += entry.Time.Format("2006-01-02 15:04:05") + " (" + entry.Level.String() + "): " + entry.Message + "\r\n" + // We don't use fields in watchtower, so don't bother sending them. + } + + return body +} + +func (e *shoutrrrTypeNotifier) sendEntries(entries []*log.Entry) { + // Do the sending in a separate goroutine so we don't block the main process. + msg := e.buildMessage(entries) + go func() { + for _, url := range e.Urls { + err := shoutrrr.Send(url, msg) + if err != nil { + // Use fmt so it doesn't trigger another notification. + fmt.Println("Failed to send notification via shoutrrr (url="+url+"): ", err) + } + } + }() +} + +func (e *shoutrrrTypeNotifier) StartNotification() { + if e.entries == nil { + e.entries = make([]*log.Entry, 0, 10) + } +} + +func (e *shoutrrrTypeNotifier) SendNotification() { + if e.entries == nil || len(e.entries) <= 0 { + return + } + + e.sendEntries(e.entries) + e.entries = nil +} + +func (e *shoutrrrTypeNotifier) Levels() []log.Level { + return e.logLevels +} + +func (e *shoutrrrTypeNotifier) Fire(entry *log.Entry) error { + if e.entries != nil { + e.entries = append(e.entries, entry) + } else { + // Log output generated outside a cycle is sent immediately. + e.sendEntries([]*log.Entry{entry}) + } + return nil +} From 59ce378a352f91d30f321e7a650c4ad9a4076cd5 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 13:53:30 +0100 Subject: [PATCH 3/9] Adjust flags --- docs/notifications.md | 6 +++--- internal/flags/flags.go | 4 ++-- pkg/notifications/shoutrrr.go | 2 +- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/docs/notifications.md b/docs/notifications.md index 6a1a9e9..32ada29 100644 --- a/docs/notifications.md +++ b/docs/notifications.md @@ -121,7 +121,7 @@ docker run -d \ To send notifications via shoutrrr, the following command-line options, or their corresponding environment variables, can be set: -- `--notification-shoutrrr-url` (env. `WATCHTOWER_NOTIFICATION_SHOUTRRR_URL`): The shoutrrr service URL to be used. +- `--notification-url` (env. `WATCHTOWER_NOTIFICATION_URL`): The shoutrrr service URL to be used. Go to [https://github.com/containrrr/shoutrrr#service-urls](https://github.com/containrrr/shoutrrr#service-urls) to learn more about the different service URLs you can use. @@ -132,7 +132,7 @@ docker run -d \ --name watchtower \ -v /var/run/docker.sock:/var/run/docker.sock \ -e WATCHTOWER_NOTIFICATIONS=shoutrrr \ - -e WATCHTOWER_NOTIFICATION_SHOUTRRR_URL=discord://channel/token \ - -e WATCHTOWER_NOTIFICATION_SHOUTRRR_URL=slack://watchtower@token-a/token-b/token-c \ + -e WATCHTOWER_NOTIFICATION_URL=discord://channel/token \ + -e WATCHTOWER_NOTIFICATION_URL=slack://watchtower@token-a/token-b/token-c \ containrrr/watchtower ``` \ No newline at end of file diff --git a/internal/flags/flags.go b/internal/flags/flags.go index 4d54f92..29c0913 100644 --- a/internal/flags/flags.go +++ b/internal/flags/flags.go @@ -240,9 +240,9 @@ Should only be used for testing. "The Gotify Application required to query the Gotify API") flags.StringArrayP( - "notification-shoutrrr-url", + "notification-url", "", - viper.GetStringSlice("WATCHTOWER_NOTIFICATION_SHOUTRRR_URL"), + viper.GetStringSlice("WATCHTOWER_NOTIFICATION_URL"), "The shoutrrr URL to send notifications to") } diff --git a/pkg/notifications/shoutrrr.go b/pkg/notifications/shoutrrr.go index 4c7d2ab..a7d786c 100644 --- a/pkg/notifications/shoutrrr.go +++ b/pkg/notifications/shoutrrr.go @@ -22,7 +22,7 @@ type shoutrrrTypeNotifier struct { func newShoutrrrNotifier(c *cobra.Command, acceptedLogLevels []log.Level) t.Notifier { flags := c.PersistentFlags() - urls, _ := flags.GetStringArray("notification-shoutrrr-url") + urls, _ := flags.GetStringArray("notification-url") n := &shoutrrrTypeNotifier{ Urls: urls, From 5869bc52aa6be669d7d0b79bb21afb2f46bf8fff Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 14:27:09 +0100 Subject: [PATCH 4/9] Use CreateSender instead of calling Send multiple times --- pkg/notifications/shoutrrr.go | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/pkg/notifications/shoutrrr.go b/pkg/notifications/shoutrrr.go index a7d786c..869ce54 100644 --- a/pkg/notifications/shoutrrr.go +++ b/pkg/notifications/shoutrrr.go @@ -48,11 +48,13 @@ func (e *shoutrrrTypeNotifier) sendEntries(entries []*log.Entry) { // Do the sending in a separate goroutine so we don't block the main process. msg := e.buildMessage(entries) go func() { - for _, url := range e.Urls { - err := shoutrrr.Send(url, msg) + router, _ := shoutrrr.CreateSender(e.Urls...) + errs := router.Send(msg, nil) + + for i, err := range errs { if err != nil { // Use fmt so it doesn't trigger another notification. - fmt.Println("Failed to send notification via shoutrrr (url="+url+"): ", err) + fmt.Println("Failed to send notification via shoutrrr (url="+e.Urls[i]+"): ", err) } } }() From b5df48279ca7e5083ab7a335d29fbf1f61a84780 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 14:34:36 +0100 Subject: [PATCH 5/9] Adjust documentation --- docs/notifications.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/notifications.md b/docs/notifications.md index 32ada29..c2a92a1 100644 --- a/docs/notifications.md +++ b/docs/notifications.md @@ -124,6 +124,7 @@ To send notifications via shoutrrr, the following command-line options, or their - `--notification-url` (env. `WATCHTOWER_NOTIFICATION_URL`): The shoutrrr service URL to be used. Go to [https://github.com/containrrr/shoutrrr#service-urls](https://github.com/containrrr/shoutrrr#service-urls) to learn more about the different service URLs you can use. +You can define multiple services by space separating the URLs. (See example below) Example: @@ -132,7 +133,6 @@ docker run -d \ --name watchtower \ -v /var/run/docker.sock:/var/run/docker.sock \ -e WATCHTOWER_NOTIFICATIONS=shoutrrr \ - -e WATCHTOWER_NOTIFICATION_URL=discord://channel/token \ - -e WATCHTOWER_NOTIFICATION_URL=slack://watchtower@token-a/token-b/token-c \ + -e WATCHTOWER_NOTIFICATION_URL="discord://channel/token slack://watchtower@token-a/token-b/token-c" \ containrrr/watchtower ``` \ No newline at end of file From 480f4c8ccbe34acec873cead28b60d15edec9524 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Mon, 23 Mar 2020 14:42:17 +0100 Subject: [PATCH 6/9] reuse router --- pkg/notifications/shoutrrr.go | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/pkg/notifications/shoutrrr.go b/pkg/notifications/shoutrrr.go index 869ce54..108e3b6 100644 --- a/pkg/notifications/shoutrrr.go +++ b/pkg/notifications/shoutrrr.go @@ -3,6 +3,7 @@ package notifications import ( "fmt" "github.com/containrrr/shoutrrr" + "github.com/containrrr/shoutrrr/pkg/router" t "github.com/containrrr/watchtower/pkg/types" log "github.com/sirupsen/logrus" "github.com/spf13/cobra" @@ -15,6 +16,7 @@ const ( // Implements Notifier, logrus.Hook type shoutrrrTypeNotifier struct { Urls []string + Router *router.ServiceRouter entries []*log.Entry logLevels []log.Level } @@ -23,9 +25,11 @@ func newShoutrrrNotifier(c *cobra.Command, acceptedLogLevels []log.Level) t.Noti flags := c.PersistentFlags() urls, _ := flags.GetStringArray("notification-url") + r, _ := shoutrrr.CreateSender(urls...) n := &shoutrrrTypeNotifier{ Urls: urls, + Router: r, logLevels: acceptedLogLevels, } @@ -48,8 +52,7 @@ func (e *shoutrrrTypeNotifier) sendEntries(entries []*log.Entry) { // Do the sending in a separate goroutine so we don't block the main process. msg := e.buildMessage(entries) go func() { - router, _ := shoutrrr.CreateSender(e.Urls...) - errs := router.Send(msg, nil) + errs := e.Router.Send(msg, nil) for i, err := range errs { if err != nil { From 21e8799ce3c6276490aee778bf129ceaf73e46e9 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Tue, 31 Mar 2020 11:29:49 +0200 Subject: [PATCH 7/9] Update documentation --- docs/notifications.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/notifications.md b/docs/notifications.md index c2a92a1..3698866 100644 --- a/docs/notifications.md +++ b/docs/notifications.md @@ -123,7 +123,7 @@ To send notifications via shoutrrr, the following command-line options, or their - `--notification-url` (env. `WATCHTOWER_NOTIFICATION_URL`): The shoutrrr service URL to be used. -Go to [https://github.com/containrrr/shoutrrr#service-urls](https://github.com/containrrr/shoutrrr#service-urls) to learn more about the different service URLs you can use. +Go to [containrrr.github.io/shoutrrr/services/overview](https://containrrr.github.io/shoutrrr/services/overview) to learn more about the different service URLs you can use. You can define multiple services by space separating the URLs. (See example below) Example: @@ -133,6 +133,6 @@ docker run -d \ --name watchtower \ -v /var/run/docker.sock:/var/run/docker.sock \ -e WATCHTOWER_NOTIFICATIONS=shoutrrr \ - -e WATCHTOWER_NOTIFICATION_URL="discord://channel/token slack://watchtower@token-a/token-b/token-c" \ + -e WATCHTOWER_NOTIFICATION_URL="discord://token@channel slack://watchtower@token-a/token-b/token-c" \ containrrr/watchtower ``` \ No newline at end of file From a8d453b4c7297d0bf5de58a2a0386945445a08a2 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Sun, 5 Apr 2020 11:10:47 +0200 Subject: [PATCH 8/9] update shoutrrr --- go.mod | 2 +- go.sum | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/go.mod b/go.mod index b6fad27..9d0138d 100644 --- a/go.mod +++ b/go.mod @@ -15,7 +15,7 @@ require ( github.com/cenkalti/backoff v2.2.1+incompatible // indirect github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6 // indirect github.com/containerd/continuity v0.0.0-20181203112020-004b46473808 // indirect - github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752 + github.com/containrrr/shoutrrr v0.0.0-20200404203330-157bd996ea13 github.com/docker/cli v0.0.0-20190327152802-57b27434ea29 github.com/docker/distribution v2.7.1+incompatible github.com/docker/docker v0.0.0-20190404075923-dbe4a30928d4 diff --git a/go.sum b/go.sum index f83bd71..a9aff4f 100644 --- a/go.sum +++ b/go.sum @@ -45,6 +45,8 @@ github.com/containerd/continuity v0.0.0-20181203112020-004b46473808 h1:4BX8f882b github.com/containerd/continuity v0.0.0-20181203112020-004b46473808/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752 h1:g7iPN6gYedYNetNT7pdSO2jyZWyg9f7OqIVB4wOcEh4= github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752/go.mod h1:eotQeC9bHbsf9eMUnXOU/y5bskegseWNB4PwmxRO7Wc= +github.com/containrrr/shoutrrr v0.0.0-20200404203330-157bd996ea13 h1:5KIwcRac24xehTL/xrhXNIiI9JnV2Mbfl52OgGbloIM= +github.com/containrrr/shoutrrr v0.0.0-20200404203330-157bd996ea13/go.mod h1:eotQeC9bHbsf9eMUnXOU/y5bskegseWNB4PwmxRO7Wc= github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk= github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= From d17e2887fba066916b0dce7ddfa01eab374cc831 Mon Sep 17 00:00:00 2001 From: Maximilian Brandau Date: Sun, 5 Apr 2020 11:51:44 +0200 Subject: [PATCH 9/9] remove old shoutrrr version --- go.sum | 2 -- 1 file changed, 2 deletions(-) diff --git a/go.sum b/go.sum index a9aff4f..97a634b 100644 --- a/go.sum +++ b/go.sum @@ -43,8 +43,6 @@ github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6 h1:A7RURps5t4yDU0 github.com/cloudflare/cfssl v0.0.0-20190911221928-1a911ca1b1d6/go.mod h1:yMWuSON2oQp+43nFtAV/uvKQIFpSPerB57DCt9t8sSA= github.com/containerd/continuity v0.0.0-20181203112020-004b46473808 h1:4BX8f882bXEDKfWIf0wa8HRvpnBoPszJJXL+TVbBw4M= github.com/containerd/continuity v0.0.0-20181203112020-004b46473808/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= -github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752 h1:g7iPN6gYedYNetNT7pdSO2jyZWyg9f7OqIVB4wOcEh4= -github.com/containrrr/shoutrrr v0.0.0-20200308125025-1981b9ef7752/go.mod h1:eotQeC9bHbsf9eMUnXOU/y5bskegseWNB4PwmxRO7Wc= github.com/containrrr/shoutrrr v0.0.0-20200404203330-157bd996ea13 h1:5KIwcRac24xehTL/xrhXNIiI9JnV2Mbfl52OgGbloIM= github.com/containrrr/shoutrrr v0.0.0-20200404203330-157bd996ea13/go.mod h1:eotQeC9bHbsf9eMUnXOU/y5bskegseWNB4PwmxRO7Wc= github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk=