mirror of
				https://github.com/appleboy/drone-ssh.git
				synced 2025-10-29 00:51:15 +08:00 
			
		
		
		
	Add sync mode.
Signed-off-by: Bo-Yi Wu <appleboy.tw@gmail.com>
This commit is contained in:
		
							parent
							
								
									6f1ace35bf
								
							
						
					
					
						commit
						0402162a26
					
				
							
								
								
									
										6
									
								
								main.go
									
									
									
									
									
								
							
							
						
						
									
										6
									
								
								main.go
									
									
									
									
									
								
							| @ -66,6 +66,11 @@ func main() { | |||||||
| 			EnvVar: "PLUGIN_PORT,SSH_PORT", | 			EnvVar: "PLUGIN_PORT,SSH_PORT", | ||||||
| 			Value:  22, | 			Value:  22, | ||||||
| 		}, | 		}, | ||||||
|  | 		cli.BoolFlag{ | ||||||
|  | 			Name:   "sync", | ||||||
|  | 			Usage:  "sync mode", | ||||||
|  | 			EnvVar: "PLUGIN_SYNC", | ||||||
|  | 		}, | ||||||
| 		cli.DurationFlag{ | 		cli.DurationFlag{ | ||||||
| 			Name:   "timeout,t", | 			Name:   "timeout,t", | ||||||
| 			Usage:  "connection timeout", | 			Usage:  "connection timeout", | ||||||
| @ -195,6 +200,7 @@ func run(c *cli.Context) error { | |||||||
| 			Secrets:        c.StringSlice("secrets"), | 			Secrets:        c.StringSlice("secrets"), | ||||||
| 			Envs:           c.StringSlice("envs"), | 			Envs:           c.StringSlice("envs"), | ||||||
| 			Debug:          c.Bool("debug"), | 			Debug:          c.Bool("debug"), | ||||||
|  | 			Sync:           c.Bool("sync"), | ||||||
| 			Proxy: easyssh.DefaultConfig{ | 			Proxy: easyssh.DefaultConfig{ | ||||||
| 				Key:      c.String("proxy.ssh-key"), | 				Key:      c.String("proxy.ssh-key"), | ||||||
| 				KeyPath:  c.String("proxy.key-path"), | 				KeyPath:  c.String("proxy.key-path"), | ||||||
|  | |||||||
							
								
								
									
										67
									
								
								plugin.go
									
									
									
									
									
								
							
							
						
						
									
										67
									
								
								plugin.go
									
									
									
									
									
								
							| @ -34,6 +34,7 @@ type ( | |||||||
| 		Envs           []string | 		Envs           []string | ||||||
| 		Proxy          easyssh.DefaultConfig | 		Proxy          easyssh.DefaultConfig | ||||||
| 		Debug          bool | 		Debug          bool | ||||||
|  | 		Sync           bool | ||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| 	// Plugin structure
 | 	// Plugin structure
 | ||||||
| @ -42,34 +43,7 @@ type ( | |||||||
| 	} | 	} | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
| func (p Plugin) log(host string, message ...interface{}) { | func (p Plugin) exec(host string, wg *sync.WaitGroup, errChannel chan error) { | ||||||
| 	if count := len(p.Config.Host); count == 1 { |  | ||||||
| 		fmt.Printf("%s", fmt.Sprintln(message...)) |  | ||||||
| 	} else { |  | ||||||
| 		fmt.Printf("%s: %s", host, fmt.Sprintln(message...)) |  | ||||||
| 	} |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // Exec executes the plugin.
 |  | ||||||
| func (p Plugin) Exec() error { |  | ||||||
| 	if len(p.Config.Host) == 0 && len(p.Config.UserName) == 0 { |  | ||||||
| 		return fmt.Errorf(missingHostOrUser) |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if len(p.Config.Key) == 0 && len(p.Config.Password) == 0 && len(p.Config.KeyPath) == 0 { |  | ||||||
| 		return fmt.Errorf(missingPasswordOrKey) |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	if len(p.Config.Key) != 0 && len(p.Config.Password) != 0 { |  | ||||||
| 		return fmt.Errorf(setPasswordandKey) |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 	wg := sync.WaitGroup{} |  | ||||||
| 	wg.Add(len(p.Config.Host)) |  | ||||||
| 	errChannel := make(chan error, 1) |  | ||||||
| 	finished := make(chan bool, 1) |  | ||||||
| 	for _, host := range p.Config.Host { |  | ||||||
| 		go func(host string) { |  | ||||||
| 	// Create MakeConfig instance with remote username, server address and path to private key.
 | 	// Create MakeConfig instance with remote username, server address and path to private key.
 | ||||||
| 	ssh := &easyssh.MakeConfig{ | 	ssh := &easyssh.MakeConfig{ | ||||||
| 		Server:   host, | 		Server:   host, | ||||||
| @ -141,13 +115,48 @@ func (p Plugin) Exec() error { | |||||||
| 	} | 	} | ||||||
| 
 | 
 | ||||||
| 	wg.Done() | 	wg.Done() | ||||||
| 		}(host) |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | func (p Plugin) log(host string, message ...interface{}) { | ||||||
|  | 	if count := len(p.Config.Host); count == 1 { | ||||||
|  | 		fmt.Printf("%s", fmt.Sprintln(message...)) | ||||||
|  | 	} else { | ||||||
|  | 		fmt.Printf("%s: %s", host, fmt.Sprintln(message...)) | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | // Exec executes the plugin.
 | ||||||
|  | func (p Plugin) Exec() error { | ||||||
|  | 	if len(p.Config.Host) == 0 && len(p.Config.UserName) == 0 { | ||||||
|  | 		return fmt.Errorf(missingHostOrUser) | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if len(p.Config.Key) == 0 && len(p.Config.Password) == 0 && len(p.Config.KeyPath) == 0 { | ||||||
|  | 		return fmt.Errorf(missingPasswordOrKey) | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if len(p.Config.Key) != 0 && len(p.Config.Password) != 0 { | ||||||
|  | 		return fmt.Errorf(setPasswordandKey) | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	wg := sync.WaitGroup{} | ||||||
|  | 	wg.Add(len(p.Config.Host)) | ||||||
|  | 	errChannel := make(chan error, 1) | ||||||
|  | 	finished := make(chan bool, 1) | ||||||
|  | 	for _, host := range p.Config.Host { | ||||||
|  | 		if p.Config.Sync { | ||||||
|  | 			p.exec(host, &wg, errChannel) | ||||||
|  | 		} else { | ||||||
|  | 			go p.exec(host, &wg, errChannel) | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	if !p.Config.Sync { | ||||||
| 		go func() { | 		go func() { | ||||||
| 			wg.Wait() | 			wg.Wait() | ||||||
| 			close(finished) | 			close(finished) | ||||||
| 		}() | 		}() | ||||||
|  | 	} | ||||||
| 
 | 
 | ||||||
| 	select { | 	select { | ||||||
| 	case <-finished: | 	case <-finished: | ||||||
|  | |||||||
| @ -256,3 +256,20 @@ func TestSetENV(t *testing.T) { | |||||||
| 	err := plugin.Exec() | 	err := plugin.Exec() | ||||||
| 	assert.Nil(t, err) | 	assert.Nil(t, err) | ||||||
| } | } | ||||||
|  | 
 | ||||||
|  | func TestSyncMode(t *testing.T) { | ||||||
|  | 	plugin := Plugin{ | ||||||
|  | 		Config: Config{ | ||||||
|  | 			Host:           []string{"localhost", "127.0.0.1"}, | ||||||
|  | 			UserName:       "drone-scp", | ||||||
|  | 			Port:           22, | ||||||
|  | 			KeyPath:        "./tests/.ssh/id_rsa", | ||||||
|  | 			Script:         []string{"whoami", "for i in {1..3}; do echo ${i}; sleep 1; done", "echo 'done'"}, | ||||||
|  | 			CommandTimeout: 60, | ||||||
|  | 			Sync:           true, | ||||||
|  | 		}, | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	err := plugin.Exec() | ||||||
|  | 	assert.Nil(t, err) | ||||||
|  | } | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user
	 Bo-Yi Wu
						Bo-Yi Wu