Skip to content

Commit 2bb3a37

Browse files
author
David Pinheiro
committed
Make ip address of both local and remote optional
This change makes the ip address of both `-local` and `-remote` optional setting their value to `127.0.0.1` if not given.
1 parent 7b96055 commit 2bb3a37

File tree

4 files changed

+95
-14
lines changed

4 files changed

+95
-14
lines changed

README.md

+20
Original file line numberDiff line numberDiff line change
@@ -54,4 +54,24 @@ INFO[0000] listening on local address local_address="127.0.0.
5454
$ mole -remote 172.17.0.100:80 -server example1
5555
INFO[0000] listening on local address local_address="127.0.0.1:61305"
5656
```
57+
### Bind the local address to 127.0.0.1 by specifying only the local port
5758

59+
```sh
60+
$ mole -v -local :8080 -remote 172.17.0.100:80 -server example1
61+
DEBU[0000] cli options key= local="127.0.0.1:8080" remote="172.17.0.100:80" server=example1 v=true
62+
DEBU[0000] using ssh config file from: /home/mole/.ssh/config
63+
DEBU[0000] server: [name=example1, address=10.0.0.12:2222, user=user, key=/home/mole/.ssh/id_rsa]
64+
DEBU[0000] tunnel: [local:127.0.0.1:8080, server:10.0.0.12:2222, remote:172.17.0.100:80]
65+
INFO[0000] listening on local address local_address="127.0.0.1:8080"
66+
```
67+
68+
### Connect to a remote ip address 127.0.0.1 by specifying only the remote port
69+
70+
```sh
71+
$ mole -v -local 127.0.0.1:8080 -remote :80 -server example1
72+
DEBU[0000] cli options key= local="127.0.0.1:8080" remote="127.0.0.1:80" server=example1 v=true
73+
DEBU[0000] using ssh config file from: /home/mole/.ssh/config
74+
DEBU[0000] server: [name=example1, address=10.0.0.12:2222, user=user, key=/home/mole/.ssh/id_rsa]
75+
DEBU[0000] tunnel: [local:127.0.0.1:8080, server:10.0.0.12:2222, remote:127.0.0.1:80]
76+
INFO[0000] listening on local address local_address="127.0.0.1:8080"
77+
```

cmd/mole/main.go

+6-10
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ func (f hostFlag) String() string {
2929
}
3030

3131
func (f *hostFlag) Set(value string) error {
32-
re := regexp.MustCompile("(?P<user>.+@)?(?P<host>[0-9a-zA-Z.-]+)(?P<port>:[0-9]+)?")
32+
re := regexp.MustCompile("(?P<user>.+@)?(?P<host>[0-9a-zA-Z\\.-]+)?(?P<port>:[0-9]+)?")
3333

3434
match := re.FindStringSubmatch(value)
3535
result := make(map[string]string)
@@ -41,10 +41,6 @@ func (f *hostFlag) Set(value string) error {
4141
result[name] = match[i]
4242
}
4343

44-
if result["host"] == "" {
45-
return fmt.Errorf("error parsing argument. Host must be provided.")
46-
}
47-
4844
f.User = strings.Trim(result["user"], "@")
4945
f.Host = result["host"]
5046
f.Port = strings.Trim(result["port"], ":")
@@ -73,11 +69,11 @@ var (
7369
)
7470

7571
func init() {
76-
flag.Var(&localFlag, "local", "set local endpoint address: <host>:<port>")
77-
flag.Var(&remoteFlag, "remote", "set remote endpoing address: <host>:<port>")
72+
flag.Var(&localFlag, "local", "(optional) Set local endpoint address: [<host>]:<port>")
73+
flag.Var(&remoteFlag, "remote", "set remote endpoing address: [<host>]:<port>")
7874
flag.Var(&serverFlag, "server", "set server address: [<user>@]<host>[:<port>]")
79-
flag.StringVar(&keyFlag, "key", "", "set server authentication key file path")
80-
flag.BoolVar(&vFlag, "v", false, "increase log verbosity")
75+
flag.StringVar(&keyFlag, "key", "", "(optional) Set server authentication key file path")
76+
flag.BoolVar(&vFlag, "v", false, "(optional) Increase log verbosity")
8177
flag.BoolVar(&helpFlag, "help", false, "list all options available")
8278
flag.BoolVar(&versionFlag, "version", false, "display the mole version")
8379
}
@@ -150,7 +146,7 @@ func handleCLIOptions() int {
150146

151147
func usage() string {
152148
return `usage:
153-
mole [-v] [-local <host>:<port>] -remote <host>:<port> -server [<user>@]<host>[:<port>] [-key <key_path>]
149+
mole [-v] [-local [<host>]:<port>] -remote [<host>]:<port> -server [<user>@]<host>[:<port>] [-key <key_path>]
154150
mole -help
155151
mole -version
156152
`

tunnel/tunnel.go

+7-1
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ func NewServer(user, address, key string) (*Server, error) {
8686
}, nil
8787
}
8888

89-
// String provided a string representation os a Server.
89+
// String provided a string representation of a Server.
9090
func (s Server) String() string {
9191
return fmt.Sprintf("[name=%s, address=%s, user=%s, key=%s]", s.Name, s.Address, s.User, s.Key)
9292
}
@@ -105,6 +105,12 @@ func New(localAddress string, server *Server, remoteAddress string) *Tunnel {
105105

106106
if localAddress == "" {
107107
localAddress = "127.0.0.1:0"
108+
} else if strings.HasPrefix(localAddress, ":") {
109+
localAddress = fmt.Sprintf("127.0.0.1%s", localAddress)
110+
}
111+
112+
if strings.HasPrefix(remoteAddress, ":") {
113+
remoteAddress = fmt.Sprintf("127.0.0.1%s", remoteAddress)
108114
}
109115

110116
return &Tunnel{

tunnel/tunnel_test.go

+62-3
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,11 @@ func TestServerOptions(t *testing.T) {
3131
}{
3232
{
3333
"mole_user",
34-
"127.0.0.1:2222",
34+
"172.17.0.10:2222",
3535
"testdata/.ssh/id_rsa",
3636
&Server{
37-
Name: "127.0.0.1",
38-
Address: "127.0.0.1:2222",
37+
Name: "172.17.0.10",
38+
Address: "172.17.0.10:2222",
3939
User: "mole_user",
4040
Key: "testdata/.ssh/id_rsa",
4141
},
@@ -88,6 +88,65 @@ func TestServerOptions(t *testing.T) {
8888

8989
}
9090

91+
func TestTunnelOptions(t *testing.T) {
92+
server := &Server{Name: "s"}
93+
tests := []struct {
94+
local string
95+
server *Server
96+
remote string
97+
expected *Tunnel
98+
}{
99+
{
100+
"172.17.0.10:2222",
101+
server,
102+
"172.17.0.10:2222",
103+
&Tunnel{
104+
local: "172.17.0.10:2222",
105+
server: server,
106+
remote: "172.17.0.10:2222",
107+
},
108+
},
109+
{
110+
"",
111+
server,
112+
"172.17.0.10:2222",
113+
&Tunnel{
114+
local: "127.0.0.1:0",
115+
server: server,
116+
remote: "172.17.0.10:2222",
117+
},
118+
},
119+
{
120+
":8443",
121+
server,
122+
":443",
123+
&Tunnel{
124+
local: "127.0.0.1:8443",
125+
server: server,
126+
remote: "127.0.0.1:443",
127+
},
128+
},
129+
}
130+
131+
for _, test := range tests {
132+
tun := New(test.local, test.server, test.remote)
133+
134+
if test.expected.local != tun.local {
135+
t.Errorf("unexpected local result : expected: %s, result: %s", test.expected, tun)
136+
}
137+
138+
if test.expected.remote != tun.remote {
139+
t.Errorf("unexpected remote result : expected: %s, result: %s", test.expected, tun)
140+
}
141+
142+
if !reflect.DeepEqual(test.expected.server, tun.server) {
143+
t.Errorf("unexpected server result : expected: %s, result: %s", test.expected, tun)
144+
}
145+
146+
}
147+
148+
}
149+
91150
func TestTunnel(t *testing.T) {
92151
expected := "ABC"
93152
c := prepareTunnel(t)

0 commit comments

Comments
 (0)