Skip to content

Commit

Permalink
new: Keep privacy of users censoring credentials
Browse files Browse the repository at this point in the history
When debugging is turned on, anything resembling an email address or the
password in the LOGIN of the IMAP client is fully censored.
  • Loading branch information
shackra committed Apr 28, 2024
1 parent c436d4b commit bf146db
Show file tree
Hide file tree
Showing 5 changed files with 74 additions and 6 deletions.
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -227,5 +227,5 @@ $RECYCLE.BIN/
*.lnk

# End of https://www.gitignore.io/api/emacs,linux,macos,windows,go,python
/local.conf
/local*.conf
/.pre-commit-config.yaml
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,7 @@ You can also use xoauth2 instead of password based authentication by setting the
-conf string
Configuration file (default "${HOME}/.config/goimapnotify/goimapnotify.conf")
-debug
Output all network activity to the terminal (!! this may leak passwords !!)
Output all network activity to the terminal (!! this won't leak your credentials !!)
-list
List all mailboxes and exit
-wait int
Expand Down
20 changes: 18 additions & 2 deletions client.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,12 @@ package main
import (
"crypto/tls"
"fmt"
"io"
"os"
"os/signal"
"syscall"

"github.com/emersion/go-imap-idle"
idle "github.com/emersion/go-imap-idle"
"github.com/emersion/go-imap/client"
"github.com/emersion/go-sasl"
)
Expand All @@ -46,7 +49,20 @@ func newClient(conf NotifyConfig) (c *client.Client, err error) {

// turn on debugging
if conf.Debug {
c.SetDebug(os.Stdout)
pr, pw := io.Pipe()

sigChan := make(chan os.Signal, 1)

signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM)

go func() {
<-sigChan
pr.Close() // close the pipe when the program is about to close
}()

go censorCredentials(pr, os.Stdout)

c.SetDebug(pw)
}

if conf.TLS && conf.TLSOptions.STARTTLS {
Expand Down
48 changes: 48 additions & 0 deletions log.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
package main

import (
"bufio"
"io"
"regexp"

"github.com/sirupsen/logrus"
)

var (
emailRegexp = regexp.MustCompile(`[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}`)
detectPasswordInLOGIN = regexp.MustCompile(`^(.*LOGIN\s+\S+\s+)"[^"]+"(.*)$`)
)

func censorCredentials(in io.Reader, out io.Writer) {
scanner := bufio.NewScanner(in)
for scanner.Scan() {
line := scanner.Text()
censoredLine := censorEmailAddress(censorPasswordInLogin(line))

_, err := out.Write([]byte(censoredLine + "\n"))

if err != nil {
logrus.Errorf("unable to write censored lines: %v", err)
}
}
}

func censorPasswordInLogin(in string) string {
matches := detectPasswordInLOGIN.FindStringSubmatch(in)

if len(matches) == 0 {
return in
}

return matches[1] + `"****"` + matches[2]
}

func censorEmailAddress(in string) string {
matches := emailRegexp.FindAllString(in, -1)

if len(matches) == 0 {
return in
}

return emailRegexp.ReplaceAllString(in, "*******@*****.***")
}
8 changes: 6 additions & 2 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ func main() {
// imap.DefaultLogMask = imap.LogConn | imap.LogRaw
fileconf := flag.String("conf", filepath.Join(getDefaultConfigPath(), "goimapnotify.conf"), "Configuration file")
list := flag.Bool("list", false, "List all mailboxes and exit")
debug := flag.Bool("debug", false, "Output all network activity to the terminal (!! this may leak passwords !!)")
debug := flag.Bool("debug", false, "Output all network activity to the terminal (!! this won't leak your credentials !!)")
wait := flag.Int("wait", 1, "Period in seconds between IDLE event and execution of scripts")

flag.Parse()
Expand Down Expand Up @@ -88,7 +88,11 @@ func main() {
config[i] = retrieveCmd(config[i])
config[i].Debug = *debug
if config[i].Alias == "" {
config[i].Alias = config[i].Username
if *debug {
config[i].Alias = censorEmailAddress(config[i].Username)
} else {
config[i].Alias = config[i].Username
}
}

if *list {
Expand Down

0 comments on commit bf146db

Please sign in to comment.