Compare commits

..

5 Commits
0.4.2 ... 0.4.3

Author SHA1 Message Date
yusing
c445d50221 smarter port selection 2024-03-29 13:55:28 +00:00
yusing
73dfc17a82 smarter port selection 2024-03-29 13:35:10 +00:00
yusing
fdab026a3b fix docker port discovery 2024-03-29 13:20:44 +00:00
yusing
c789c69c86 codemirror 5 fix for config edit 2024-03-29 13:13:26 +00:00
Yuzerion
2b298aa7fa Update README.md 2024-03-29 21:01:18 +08:00
10 changed files with 81 additions and 26 deletions

2
.gitignore vendored
View File

@@ -4,5 +4,7 @@ config/**
bin/go-proxy.bak
templates/codemirror/
logs/
log/

3
.gitmodules vendored
View File

@@ -1,3 +0,0 @@
[submodule "templates/codemirror"]
path = templates/codemirror
url = https://github.com/codemirror/codemirror5.git

View File

@@ -7,7 +7,13 @@ setup:
[ -f config/config.yml ] || cp config.example.yml config/config.yml
[ -f config/providers.yml ] || touch config/providers.yml
[ -f compose.yml ] || cp compose.example.yml compose.yml
setup-codemirror:
wget https://codemirror.net/5/codemirror.zip
unzip codemirror.zip
rm codemirror.zip
mv codemirror-* templates/codemirror
build:
mkdir -p bin
CGO_ENABLED=0 GOOS=linux go build -pgo=auto -o bin/go-proxy src/go-proxy/*.go

View File

@@ -67,7 +67,9 @@ In the examples domain `x.y.z` is used, replace them with your domain
4. Start `go-proxy` (see [Binary](#binary) or [docker](#docker))
5. Start editing config files
5. (Optional) `make setup-codemirror` in case you use the web config editor
6. Start editing config files
- with text editor (i.e. Visual Studio Code)
- with web config editor by navigate to `ip:8080`

Binary file not shown.

View File

@@ -12,7 +12,7 @@ import (
)
var (
ImageNamePortMap = map[string]string{
ImageNamePortMapTCP = map[string]string{
"postgres": "5432",
"mysql": "3306",
"mariadb": "3306",
@@ -22,7 +22,7 @@ var (
"rabbitmq": "5672",
"mongo": "27017",
}
ExtraNamePortMap = map[string]string{
ExtraNamePortMapTCP = map[string]string{
"dns": "53",
"ssh": "22",
"ftp": "21",
@@ -30,18 +30,44 @@ var (
"pop3": "110",
"imap": "143",
}
NamePortMap = func() map[string]string {
NamePortMapTCP = func() map[string]string {
m := make(map[string]string)
for k, v := range ImageNamePortMap {
for k, v := range ImageNamePortMapTCP {
m[k] = v
}
for k, v := range ExtraNamePortMap {
for k, v := range ExtraNamePortMapTCP {
m[k] = v
}
return m
}()
)
var ImageNamePortMapHTTP = map[string]uint16{
"nginx": 80,
"httpd": 80,
"adguardhome": 3000,
"gogs": 3000,
"gitea": 3000,
"portainer": 9000,
"portainer-ce": 9000,
"home-assistant": 8123,
"homebridge": 8581,
"uptime-kuma": 3001,
"changedetection.io": 3000,
"prometheus": 9090,
"grafana": 3000,
"dockge": 5001,
"nginx-proxy-manager": 81,
}
var wellKnownHTTPPorts = map[uint16]bool{
80: true,
8000: true,
8008: true,
8080: true,
3000: true,
}
var (
StreamSchemes = []string{StreamType_TCP, StreamType_UDP} // TODO: support "tcp:udp", "udp:tcp"
HTTPSchemes = []string{"http", "https"}
@@ -92,6 +118,7 @@ var (
Timeout: 5 * time.Second,
KeepAlive: 5 * time.Second,
}).DialContext,
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
},
}
)
@@ -147,4 +174,4 @@ var logLevel = func() logrus.Level {
logrus.SetLevel(logrus.DebugLevel)
}
return logrus.GetLevel()
}()
}()

View File

@@ -23,7 +23,7 @@ func (p *Provider) setConfigField(c *ProxyConfig, label string, value string, pr
return nil
}
func (p *Provider) getContainerProxyConfigs(container types.Container, clientIP string) ProxyConfigSlice {
func (p *Provider) getContainerProxyConfigs(container *types.Container, clientIP string) ProxyConfigSlice {
var aliases []string
cfgs := make(ProxyConfigSlice, 0)
@@ -64,7 +64,7 @@ func (p *Provider) getContainerProxyConfigs(container types.Container, clientIP
config.Port = fmt.Sprintf("%d", selectPort(container))
}
if config.Port == "0" {
l.Debugf("no ports exposed, ignored")
l.Infof("no ports exposed, ignored")
continue
}
if config.Scheme == "" {
@@ -74,10 +74,8 @@ func (p *Provider) getContainerProxyConfigs(container types.Container, clientIP
case strings.HasPrefix(container.Image, "sha256:"):
config.Scheme = "http"
default:
imageSplit := strings.Split(container.Image, "/")
imageSplit = strings.Split(imageSplit[len(imageSplit)-1], ":")
imageName := imageSplit[0]
_, isKnownImage := ImageNamePortMap[imageName]
imageName := getImageName(container)
_, isKnownImage := ImageNamePortMapTCP[imageName]
if isKnownImage {
config.Scheme = "tcp"
} else {
@@ -182,25 +180,46 @@ func (p *Provider) getDockerProxyConfigs() (ProxyConfigSlice, error) {
cfgs := make(ProxyConfigSlice, 0)
for _, container := range containerSlice {
cfgs = append(cfgs, p.getContainerProxyConfigs(container, clientIP)...)
cfgs = append(cfgs, p.getContainerProxyConfigs(&container, clientIP)...)
}
return cfgs, nil
}
// var dockerUrlRegex = regexp.MustCompile(`^(?P<scheme>\w+)://(?P<host>[^:]+)(?P<port>:\d+)?(?P<path>/.*)?$`)
func getImageName(c *types.Container) string {
imageSplit := strings.Split(c.Image, "/")
imageSplit = strings.Split(imageSplit[len(imageSplit)-1], ":")
return imageSplit[0]
}
func getPublicPort(p types.Port) uint16 { return p.PublicPort }
func getPrivatePort(p types.Port) uint16 { return p.PrivatePort }
func selectPort(c types.Container) uint16 {
func selectPort(c *types.Container) uint16 {
if c.HostConfig.NetworkMode == "host" {
return selectPortInternal(c, getPrivatePort)
return selectPortInternal(c, getPublicPort)
}
return selectPortInternal(c, getPublicPort)
return selectPortInternal(c, getPrivatePort)
}
func selectPortInternal(c types.Container, getPort func(types.Port) uint16) uint16 {
func selectPortInternal(c *types.Container, getPort func(types.Port) uint16) uint16 {
imageName := getImageName(c)
// if is known image -> use known port
if port, isKnown := ImageNamePortMapHTTP[imageName]; isKnown {
for _, p := range c.Ports {
if p.PrivatePort == port {
return getPort(p)
}
}
}
// if it has known http port -> use it
for _, p := range c.Ports {
if isWellKnownHTTPPort(p.PrivatePort) {
return getPort(p)
}
}
// if it has any port -> use it
for _, p := range c.Ports {
if port := getPort(p); port != 0 {
return port
@@ -208,3 +227,8 @@ func selectPortInternal(c types.Container, getPort func(types.Port) uint16) uint
}
return 0
}
func isWellKnownHTTPPort(port uint16) bool {
_, ok := wellKnownHTTPPorts[port]
return ok
}

View File

@@ -37,8 +37,6 @@ func main() {
cfg = NewConfig(configPath)
cfg.MustLoad()
logrus.Info(cfg.Value())
if args.Command == CommandValidate {
logrus.Printf("config OK")
return

View File

@@ -58,7 +58,7 @@ func newStreamRouteBase(config *ProxyConfig) (*StreamRouteBase, error) {
dstPort = portSplit[1]
}
if port, hasName := NamePortMap[dstPort]; hasName {
if port, hasName := NamePortMapTCP[dstPort]; hasName {
dstPort = port
}