Skip to content

Commit

Permalink
Add proxy options to config
Browse files Browse the repository at this point in the history
  • Loading branch information
tulir committed May 20, 2024
1 parent 394e46d commit 74e5984
Show file tree
Hide file tree
Showing 6 changed files with 73 additions and 15 deletions.
4 changes: 4 additions & 0 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,10 @@ type Config struct {
WhatsApp struct {
OSName string `yaml:"os_name"`
BrowserName string `yaml:"browser_name"`

Proxy string `yaml:"proxy"`
GetProxyURL string `yaml:"get_proxy_url"`
ProxyOnlyLogin bool `yaml:"proxy_only_login"`
} `yaml:"whatsapp"`

Bridge BridgeConfig `yaml:"bridge"`
Expand Down
3 changes: 3 additions & 0 deletions config/upgrade.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,9 @@ func DoUpgrade(helper *up.Helper) {

helper.Copy(up.Str, "whatsapp", "os_name")
helper.Copy(up.Str, "whatsapp", "browser_name")
helper.Copy(up.Str|up.Null, "whatsapp", "proxy")
helper.Copy(up.Str|up.Null, "whatsapp", "get_proxy_url")
helper.Copy(up.Bool, "whatsapp", "proxy_only_login")

helper.Copy(up.Str, "bridge", "username_template")
helper.Copy(up.Str, "bridge", "displayname_template")
Expand Down
6 changes: 6 additions & 0 deletions example-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,12 @@ whatsapp:
# Must be "unknown" for a generic icon or a valid browser name if you want a specific icon.
# List of valid browser names: https://github.com/tulir/whatsmeow/blob/efc632c008604016ddde63bfcfca8de4e5304da9/binary/proto/def.proto#L43-L64
browser_name: unknown
# Proxy to use for all WhatsApp connections.
proxy: null
# Alternative to proxy: an HTTP endpoint that returns the proxy URL to use for WhatsApp connections.
get_proxy_url: null
# Whether the proxy options should only apply to the login websocket and not to authenticated connections.
proxy_only_login: false

# Bridge config
bridge:
Expand Down
10 changes: 5 additions & 5 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,10 @@ require (
github.com/tidwall/gjson v1.17.1
go.mau.fi/util v0.4.2
go.mau.fi/webp v0.1.0
go.mau.fi/whatsmeow v0.0.0-20240327124018-350073db195c
go.mau.fi/whatsmeow v0.0.0-20240520084720-d900d6f2af0f
golang.org/x/exp v0.0.0-20240409090435-93d18d7e34b8
golang.org/x/image v0.15.0
golang.org/x/net v0.24.0
golang.org/x/net v0.25.0
golang.org/x/sync v0.7.0
google.golang.org/protobuf v1.33.0
maunium.net/go/mautrix v0.18.1
Expand All @@ -42,9 +42,9 @@ require (
github.com/yuin/goldmark v1.7.1 // indirect
go.mau.fi/libsignal v0.1.0 // indirect
go.mau.fi/zeroconfig v0.1.2 // indirect
golang.org/x/crypto v0.22.0 // indirect
golang.org/x/sys v0.19.0 // indirect
golang.org/x/text v0.14.0 // indirect
golang.org/x/crypto v0.23.0 // indirect
golang.org/x/sys v0.20.0 // indirect
golang.org/x/text v0.15.0 // indirect
gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
maunium.net/go/mauflag v1.0.0 // indirect
Expand Down
20 changes: 10 additions & 10 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -73,27 +73,27 @@ go.mau.fi/util v0.4.2 h1:RR3TOcRHmCF9Bx/3YG4S65MYfa+nV6/rn8qBWW4Mi30=
go.mau.fi/util v0.4.2/go.mod h1:PlAVfUUcPyHPrwnvjkJM9UFcPE7qGPDJqk+Oufa1Gtw=
go.mau.fi/webp v0.1.0 h1:BHObH/DcFntT9KYun5pDr0Ot4eUZO8k2C7eP7vF4ueA=
go.mau.fi/webp v0.1.0/go.mod h1:e42Z+VMFrUMS9cpEwGRIor+lQWO8oUAyPyMtcL+NMt8=
go.mau.fi/whatsmeow v0.0.0-20240327124018-350073db195c h1:a5O4nqmwUWvmC+27RUdefkuy5XzMOEUqR9ji+/BcHZA=
go.mau.fi/whatsmeow v0.0.0-20240327124018-350073db195c/go.mod h1:kNI5foyzqd77d5HaWc1Jico6/rxtZ/UE8nr80hIsbIk=
go.mau.fi/whatsmeow v0.0.0-20240520084720-d900d6f2af0f h1:ZqNMbb/XIAANkOn/c0FzFjm75pbTtNYyide3jGl2ptQ=
go.mau.fi/whatsmeow v0.0.0-20240520084720-d900d6f2af0f/go.mod h1:0+65CYaE6r4dWzr0dN8i+UZKy0gIfJ79VuSqIl0nKRM=
go.mau.fi/zeroconfig v0.1.2 h1:DKOydWnhPMn65GbXZOafgkPm11BvFashZWLct0dGFto=
go.mau.fi/zeroconfig v0.1.2/go.mod h1:NcSJkf180JT+1IId76PcMuLTNa1CzsFFZ0nBygIQM70=
golang.org/x/crypto v0.22.0 h1:g1v0xeRhjcugydODzvb3mEM9SQ0HGp9s/nh3COQ/C30=
golang.org/x/crypto v0.22.0/go.mod h1:vr6Su+7cTlO45qkww3VDJlzDn0ctJvRgYbC2NvXHt+M=
golang.org/x/crypto v0.23.0 h1:dIJU/v2J8Mdglj/8rJ6UUOM3Zc9zLZxVZwwxMooUSAI=
golang.org/x/crypto v0.23.0/go.mod h1:CKFgDieR+mRhux2Lsu27y0fO304Db0wZe70UKqHu0v8=
golang.org/x/exp v0.0.0-20240409090435-93d18d7e34b8 h1:ESSUROHIBHg7USnszlcdmjBEwdMj9VUvU+OPk4yl2mc=
golang.org/x/exp v0.0.0-20240409090435-93d18d7e34b8/go.mod h1:/lliqkxwWAhPjf5oSOIJup2XcqJaw8RGS6k3TGEc7GI=
golang.org/x/image v0.15.0 h1:kOELfmgrmJlw4Cdb7g/QGuB3CvDrXbqEIww/pNtNBm8=
golang.org/x/image v0.15.0/go.mod h1:HUYqC05R2ZcZ3ejNQsIHQDQiwWM4JBqmm6MKANTp4LE=
golang.org/x/net v0.24.0 h1:1PcaxkF854Fu3+lvBIx5SYn9wRlBzzcnHZSiaFFAb0w=
golang.org/x/net v0.24.0/go.mod h1:2Q7sJY5mzlzWjKtYUEXSlBWCdyaioyXzRB2RtU8KVE8=
golang.org/x/net v0.25.0 h1:d/OCCoBEUq33pjydKrGQhw7IlUPI2Oylr+8qLx49kac=
golang.org/x/net v0.25.0/go.mod h1:JkAGAh7GEvH74S6FOH42FLoXpXbE/aqXSrIQjXgsiwM=
golang.org/x/sync v0.7.0 h1:YsImfSBoP9QPYL0xyKJPq0gcaJdG3rInoqxTWbfQu9M=
golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.19.0 h1:q5f1RH2jigJ1MoAWp2KTp3gm5zAGFUTarQZ5U386+4o=
golang.org/x/sys v0.19.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ=
golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
golang.org/x/sys v0.20.0 h1:Od9JTbYCk261bKm4M/mw7AklTlFYIa0bIp9BgSm1S8Y=
golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/text v0.15.0 h1:h1V/4gjBv8v9cjcR6+AR5+/cIYK5N/WAgiv4xlsEtAk=
golang.org/x/text v0.15.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
google.golang.org/protobuf v1.33.0 h1:uNO2rsAINq/JlFpSdYEKIZ0uKD/R9cpdv0T+yoGwGmI=
google.golang.org/protobuf v1.33.0/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
Expand Down
45 changes: 45 additions & 0 deletions user.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ import (
"math"
"math/rand"
"net/http"
"net/url"
"strconv"
"strings"
"sync"
Expand Down Expand Up @@ -556,6 +557,50 @@ func (user *User) createClient(sess *store.Device) {
user.bridge.Metrics.TrackRetryReceipt(retryCount, true)
return true
}
if !user.bridge.Config.WhatsApp.ProxyOnlyLogin || sess.ID == nil {
if proxy, err := user.getProxy("login"); err != nil {
user.zlog.Err(err).Msg("Failed to get proxy address")
} else if err = user.Client.SetProxyAddress(proxy); err != nil {
user.zlog.Err(err).Msg("Failed to set proxy address")
}
}
if user.bridge.Config.WhatsApp.ProxyOnlyLogin {
user.Client.ToggleProxyOnlyForLogin(true)
}
}

type respGetProxy struct {
ProxyURL string `json:"proxy_url"`
}

func (user *User) getProxy(reason string) (string, error) {
if user.bridge.Config.WhatsApp.GetProxyURL == "" {
return user.bridge.Config.WhatsApp.Proxy, nil
}
parsed, err := url.Parse(user.bridge.Config.WhatsApp.GetProxyURL)
if err != nil {
return "", fmt.Errorf("failed to parse address: %w", err)
}
q := parsed.Query()
q.Set("reason", reason)
parsed.RawQuery = q.Encode()
req, err := http.NewRequest(http.MethodGet, parsed.String(), nil)
if err != nil {
return "", fmt.Errorf("failed to prepare request: %w", err)
}
req.Header.Set("User-Agent", mautrix.DefaultUserAgent)
resp, err := http.DefaultClient.Do(req)
if err != nil {
return "", fmt.Errorf("failed to send request: %w", err)
} else if resp.StatusCode >= 300 || resp.StatusCode < 200 {
return "", fmt.Errorf("unexpected status code %d", resp.StatusCode)
}
var respData respGetProxy
err = json.NewDecoder(resp.Body).Decode(&respData)
if err != nil {
return "", fmt.Errorf("failed to decode response: %w", err)
}
return respData.ProxyURL, nil
}

func (user *User) Login(ctx context.Context) (<-chan whatsmeow.QRChannelItem, error) {
Expand Down

0 comments on commit 74e5984

Please sign in to comment.