/* tofuproxy -- HTTP proxy with TLS certificates management Copyright (C) 2021 Sergey Matveev 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, version 3 of the License. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ package tofuproxy import ( "bytes" "errors" "fmt" "io/ioutil" "log" "os" "os/exec" "path/filepath" "strings" ) func findInNetrc(host string) (string, string) { netrcPath, ok := os.LookupEnv("NETRC") if !ok { netrcPath = filepath.Join(os.Getenv("HOME"), ".netrc") } data, err := ioutil.ReadFile(netrcPath) if err != nil { if os.IsNotExist(err) { return "", "" } log.Fatalln(err) } var login string var password string for _, line := range strings.Split(string(data), "\n") { if i := strings.Index(line, "#"); i >= 0 { line = line[:i] } f := strings.Fields(line) if len(f) >= 6 && f[0] == "machine" && f[1] == host && f[2] == "login" && f[4] == "password" { login, password = f[3], f[5] break } } return login, password } func authDialog(host, realm string) (string, string, error) { var b bytes.Buffer userInit, passInit := findInNetrc(host) b.WriteString(fmt.Sprintf(` tk_setPalette grey wm title . "Unauthorized: %s" label .luser -text "User" set userinit "%s" set u [entry .user -textvariable userinit] grid .luser .user label .lpass -text "Password" set passinit "%s" set p [entry .pass -show "*" -textvariable passinit] grid .lpass .pass proc submit {} { global u p puts [$u get] puts [$p get] exit } button .submit -text "Submit" -command submit grid .submit `, realm, userInit, passInit)) cmd := exec.Command(CmdWish) cmd.Stdin = &b out, err := cmd.Output() if err != nil { return "", "", err } lines := strings.Split(string(out), "\n") if len(lines) < 2 { return "", "", errors.New("invalid output from authorization form") } return lines[0], lines[1], nil }