diff --git a/sshpiperd/pipemgr.go b/sshpiperd/pipemgr.go index 5810da7a..1014fb16 100644 --- a/sshpiperd/pipemgr.go +++ b/sshpiperd/pipemgr.go @@ -22,10 +22,23 @@ func createPipeMgr(driver *string) interface{} { } `command:"list" description:"list all pipes"` Add struct { subCommand + + PiperUserName string `long:"piper-username" description:"" required:"true" no-ini:"true"` + // PiperAuthorizedKeysFile flags.Filename + + UpstreamUserName string `long:"upstream-username" description:"mapped user name" no-ini:"true"` + UpstreamHost string `long:"host" description:"upstream sshd host" required:"true" no-ini:"true"` + UpstreamPort uint `long:"port" description:"upstream sshd port" default:"22" no-ini:"true"` + // UpstreamKeyFile flags.Filename + + // UpstreamHostKey + // MapType + } `command:"add" description:"add a pipe to current upstream"` Remove struct { subCommand - Name string `long:"name" required:"true"` + + Name string `long:"name" required:"true" no-ini:"true"` } `command:"remove" description:"remove a pipe from current upstream"` }{} @@ -34,22 +47,30 @@ func createPipeMgr(driver *string) interface{} { } pipeMgrCmd.Add.callback = func(args []string) error { - return nil + p, err := load() + if err != nil { + return err + } + + opt := pipeMgrCmd.Add + + return p.CreatePipe(upstream.CreatePipeOption{ + Username: opt.PiperUserName, + UpstreamUsername: opt.UpstreamUserName, + Host: opt.UpstreamHost, + Port: opt.UpstreamPort, + }) } pipeMgrCmd.Remove.callback = func(args []string) error { - p, err := load() - name := pipeMgrCmd.Remove.Name - + p, err := load() if err != nil { return err - } return p.RemovePipe(name) - } return &pipeMgrCmd diff --git a/sshpiperd/sshpiperd_test.go b/sshpiperd/sshpiperd_test.go index d9f16b29..f7fb35c3 100644 --- a/sshpiperd/sshpiperd_test.go +++ b/sshpiperd/sshpiperd_test.go @@ -112,6 +112,14 @@ type testupstream struct { h upstream.Handler } +func (t *testupstream) CreatePipe(opt upstream.CreatePipeOption) error { + panic("implement me") +} + +func (t *testupstream) RemovePipe(name string) error { + panic("implement me") +} + func (t *testupstream) GetHandler() upstream.Handler { return t.h } diff --git a/sshpiperd/upstream/provider.go b/sshpiperd/upstream/provider.go index 04ffb89c..0fc7ab3a 100644 --- a/sshpiperd/upstream/provider.go +++ b/sshpiperd/upstream/provider.go @@ -15,7 +15,10 @@ import ( type Handler func(conn ssh.ConnMetadata) (net.Conn, *ssh.AuthPipe, error) type CreatePipeOption struct { - + Username string + UpstreamUsername string + Host string + Port uint } // Provider is a factory for Upstream Provider diff --git a/sshpiperd/upstream/workingdir/config.go b/sshpiperd/upstream/workingdir/config.go index bb217529..df15e0a3 100644 --- a/sshpiperd/upstream/workingdir/config.go +++ b/sshpiperd/upstream/workingdir/config.go @@ -2,7 +2,7 @@ package workingdir var ( config = struct { - WorkingDir string `long:"upstream-workingdir" default:"/var/sshpiper" description:"Path to workingdir" env:"SSHPIPERD_UPSTREAM_WORKINGDIR" ini-name:"upstream-workingdir"` + WorkingDir string `long:"upstream-workingdir" default:"/var/sshpiper" description:"Path to workingdir" env:"SSHPIPERD_UPSTREAM_WORKINGDIR" ini-name:"upstream-workingdir" required:"true"` AllowBadUsername bool `long:"upstream-workingdir-allowbadusername" description:"Disable username check while search the working dir" env:"SSHPIPERD_UPSTREAM_WORKINGDIR_ALLOWBADUSERNAME" ini-name:"upstream-workingdir-allowbadusername"` NoCheckPerm bool `long:"upstream-workingdir-nocheckperm" description:"Disable 0400 checking when using files in the working dir" env:"SSHPIPERD_UPSTREAM_WORKINGDIR_NOCHECKPERM" ini-name:"upstream-workingdir-nocheckperm"` FallbackUsername string `long:"upstream-workingdir-fallbackusername" description:"Fallback to a user when user does not exists in directory" env:"SSHPIPERD_UPSTREAM_WORKINGDIR_FALLBACKUSERNAME" ini-name:"upstream-workingdir-fallbackusername"` diff --git a/sshpiperd/upstream/workingdir/plugin.go b/sshpiperd/upstream/workingdir/plugin.go index a3bc4c06..0fffb029 100644 --- a/sshpiperd/upstream/workingdir/plugin.go +++ b/sshpiperd/upstream/workingdir/plugin.go @@ -1,7 +1,10 @@ package workingdir import ( + "fmt" + "io/ioutil" "log" + "os" "github.com/tg123/sshpiper/sshpiperd/upstream" ) @@ -12,11 +15,34 @@ type plugin struct { } func (p *plugin) CreatePipe(opt upstream.CreatePipeOption) error { - panic("implement me") + err := os.MkdirAll(config.WorkingDir+"/"+opt.Username, os.ModePerm) + if err != nil { + return err + } + + path := userUpstreamFile.realPath(opt.Username) + if _, err := os.Stat(path); os.IsNotExist(err) { + + upuser := opt.UpstreamUsername + + if len(upuser) == 0 { + upuser = opt.Username + } + + content := fmt.Sprintf("%v@%v:%v", upuser, opt.Host, opt.Port) + return ioutil.WriteFile(path, []byte(content), os.ModePerm) + } + + return fmt.Errorf("upstream file alreay exists") } func (p *plugin) RemovePipe(name string) error { - panic("implement me") + path := userUpstreamFile.realPath(name) + if _, err := os.Stat(path); os.IsNotExist(err) { + return nil + } + + return os.Remove(path) } func (p *plugin) GetName() string {