cmd_provider.go 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. package worker
  2. import (
  3. "errors"
  4. "os"
  5. "time"
  6. "github.com/anmitsu/go-shlex"
  7. )
  8. type cmdConfig struct {
  9. name string
  10. upstreamURL, command string
  11. workingDir, logDir, logFile string
  12. interval time.Duration
  13. env map[string]string
  14. }
  15. type cmdProvider struct {
  16. baseProvider
  17. cmdConfig
  18. command []string
  19. cmd *cmdJob
  20. logFile *os.File
  21. }
  22. func newCmdProvider(c cmdConfig) (*cmdProvider, error) {
  23. // TODO: check config options
  24. provider := &cmdProvider{
  25. baseProvider: baseProvider{
  26. name: c.name,
  27. ctx: NewContext(),
  28. interval: c.interval,
  29. },
  30. cmdConfig: c,
  31. }
  32. provider.ctx.Set(_WorkingDirKey, c.workingDir)
  33. provider.ctx.Set(_LogDirKey, c.logDir)
  34. provider.ctx.Set(_LogFileKey, c.logFile)
  35. cmd, err := shlex.Split(c.command, true)
  36. if err != nil {
  37. return nil, err
  38. }
  39. provider.command = cmd
  40. return provider, nil
  41. }
  42. func (p *cmdProvider) Start() error {
  43. env := map[string]string{
  44. "TUNASYNC_MIRROR_NAME": p.Name(),
  45. "TUNASYNC_WORKING_DIR": p.WorkingDir(),
  46. "TUNASYNC_UPSTREAM_URL": p.upstreamURL,
  47. "TUNASYNC_LOG_FILE": p.LogFile(),
  48. }
  49. for k, v := range p.env {
  50. env[k] = v
  51. }
  52. p.cmd = newCmdJob(p.command, p.WorkingDir(), env)
  53. logFile, err := os.OpenFile(p.LogFile(), os.O_WRONLY|os.O_CREATE, 0644)
  54. if err != nil {
  55. return err
  56. }
  57. p.logFile = logFile
  58. p.cmd.SetLogFile(logFile)
  59. return p.cmd.Start()
  60. }
  61. func (p *cmdProvider) Wait() error {
  62. if p.logFile != nil {
  63. defer p.logFile.Close()
  64. }
  65. return p.cmd.Wait()
  66. }
  67. func (p *cmdProvider) Terminate() error {
  68. logger.Debug("terminating provider: %s", p.Name())
  69. if p.cmd == nil {
  70. return errors.New("provider command job not initialized")
  71. }
  72. if p.logFile != nil {
  73. p.logFile.Close()
  74. }
  75. err := p.cmd.Terminate()
  76. return err
  77. }