job_test.go 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270
  1. package worker
  2. import (
  3. "fmt"
  4. "io/ioutil"
  5. "os"
  6. "path/filepath"
  7. "testing"
  8. "time"
  9. . "github.com/smartystreets/goconvey/convey"
  10. . "github.com/tuna/tunasync/internal"
  11. )
  12. func TestMirrorJob(t *testing.T) {
  13. InitLogger(true, true, false)
  14. Convey("MirrorJob should work", t, func(ctx C) {
  15. tmpDir, err := ioutil.TempDir("", "tunasync")
  16. defer os.RemoveAll(tmpDir)
  17. So(err, ShouldBeNil)
  18. scriptFile := filepath.Join(tmpDir, "cmd.sh")
  19. tmpFile := filepath.Join(tmpDir, "log_file")
  20. c := cmdConfig{
  21. name: "tuna-cmd-jobtest",
  22. upstreamURL: "http://mirrors.tuna.moe/",
  23. command: "bash " + scriptFile,
  24. workingDir: tmpDir,
  25. logDir: tmpDir,
  26. logFile: tmpFile,
  27. interval: 1 * time.Second,
  28. }
  29. provider, err := newCmdProvider(c)
  30. So(err, ShouldBeNil)
  31. So(provider.Name(), ShouldEqual, c.name)
  32. So(provider.WorkingDir(), ShouldEqual, c.workingDir)
  33. So(provider.LogDir(), ShouldEqual, c.logDir)
  34. So(provider.LogFile(), ShouldEqual, c.logFile)
  35. So(provider.Interval(), ShouldEqual, c.interval)
  36. Convey("For a normal mirror job", func(ctx C) {
  37. scriptContent := `#!/bin/bash
  38. echo $TUNASYNC_WORKING_DIR
  39. echo $TUNASYNC_MIRROR_NAME
  40. echo $TUNASYNC_UPSTREAM_URL
  41. echo $TUNASYNC_LOG_FILE
  42. `
  43. expectedOutput := fmt.Sprintf(
  44. "%s\n%s\n%s\n%s\n",
  45. provider.WorkingDir(),
  46. provider.Name(),
  47. provider.upstreamURL,
  48. provider.LogFile(),
  49. )
  50. err = ioutil.WriteFile(scriptFile, []byte(scriptContent), 0755)
  51. So(err, ShouldBeNil)
  52. readedScriptContent, err := ioutil.ReadFile(scriptFile)
  53. So(err, ShouldBeNil)
  54. So(readedScriptContent, ShouldResemble, []byte(scriptContent))
  55. Convey("If we let it run several times", func(ctx C) {
  56. managerChan := make(chan jobMessage, 10)
  57. semaphore := make(chan empty, 1)
  58. job := newMirrorJob(provider)
  59. go job.Run(managerChan, semaphore)
  60. // job should not start if we don't start it
  61. select {
  62. case <-managerChan:
  63. So(0, ShouldEqual, 1) // made this fail
  64. case <-time.After(1 * time.Second):
  65. So(0, ShouldEqual, 0)
  66. }
  67. job.ctrlChan <- jobStart
  68. for i := 0; i < 2; i++ {
  69. msg := <-managerChan
  70. So(msg.status, ShouldEqual, PreSyncing)
  71. msg = <-managerChan
  72. So(msg.status, ShouldEqual, Syncing)
  73. msg = <-managerChan
  74. So(msg.status, ShouldEqual, Success)
  75. loggedContent, err := ioutil.ReadFile(provider.LogFile())
  76. So(err, ShouldBeNil)
  77. So(string(loggedContent), ShouldEqual, expectedOutput)
  78. job.ctrlChan <- jobStart
  79. }
  80. select {
  81. case msg := <-managerChan:
  82. So(msg.status, ShouldEqual, PreSyncing)
  83. msg = <-managerChan
  84. So(msg.status, ShouldEqual, Syncing)
  85. msg = <-managerChan
  86. So(msg.status, ShouldEqual, Success)
  87. case <-time.After(2 * time.Second):
  88. So(0, ShouldEqual, 1)
  89. }
  90. job.ctrlChan <- jobDisable
  91. select {
  92. case <-managerChan:
  93. So(0, ShouldEqual, 1) // made this fail
  94. case <-job.disabled:
  95. So(0, ShouldEqual, 0)
  96. }
  97. })
  98. })
  99. Convey("When running long jobs", func(ctx C) {
  100. scriptContent := `#!/bin/bash
  101. echo $TUNASYNC_WORKING_DIR
  102. sleep 5
  103. echo $TUNASYNC_WORKING_DIR
  104. `
  105. err = ioutil.WriteFile(scriptFile, []byte(scriptContent), 0755)
  106. So(err, ShouldBeNil)
  107. managerChan := make(chan jobMessage, 10)
  108. semaphore := make(chan empty, 1)
  109. job := newMirrorJob(provider)
  110. Convey("If we kill it", func(ctx C) {
  111. go job.Run(managerChan, semaphore)
  112. job.ctrlChan <- jobStart
  113. time.Sleep(1 * time.Second)
  114. msg := <-managerChan
  115. So(msg.status, ShouldEqual, PreSyncing)
  116. msg = <-managerChan
  117. So(msg.status, ShouldEqual, Syncing)
  118. job.ctrlChan <- jobStart // should be ignored
  119. job.ctrlChan <- jobStop
  120. msg = <-managerChan
  121. So(msg.status, ShouldEqual, Failed)
  122. expectedOutput := fmt.Sprintf("%s\n", provider.WorkingDir())
  123. loggedContent, err := ioutil.ReadFile(provider.LogFile())
  124. So(err, ShouldBeNil)
  125. So(string(loggedContent), ShouldEqual, expectedOutput)
  126. job.ctrlChan <- jobDisable
  127. <-job.disabled
  128. })
  129. Convey("If we don't kill it", func(ctx C) {
  130. go job.Run(managerChan, semaphore)
  131. job.ctrlChan <- jobStart
  132. msg := <-managerChan
  133. So(msg.status, ShouldEqual, PreSyncing)
  134. msg = <-managerChan
  135. So(msg.status, ShouldEqual, Syncing)
  136. msg = <-managerChan
  137. So(msg.status, ShouldEqual, Success)
  138. expectedOutput := fmt.Sprintf(
  139. "%s\n%s\n",
  140. provider.WorkingDir(), provider.WorkingDir(),
  141. )
  142. loggedContent, err := ioutil.ReadFile(provider.LogFile())
  143. So(err, ShouldBeNil)
  144. So(string(loggedContent), ShouldEqual, expectedOutput)
  145. job.ctrlChan <- jobDisable
  146. <-job.disabled
  147. })
  148. Convey("If we restart it", func(ctx C) {
  149. go job.Run(managerChan, semaphore)
  150. job.ctrlChan <- jobStart
  151. msg := <-managerChan
  152. So(msg.status, ShouldEqual, PreSyncing)
  153. msg = <-managerChan
  154. So(msg.status, ShouldEqual, Syncing)
  155. job.ctrlChan <- jobRestart
  156. msg = <-managerChan
  157. So(msg.status, ShouldEqual, Failed)
  158. So(msg.msg, ShouldEqual, "killed by manager")
  159. msg = <-managerChan
  160. So(msg.status, ShouldEqual, PreSyncing)
  161. msg = <-managerChan
  162. So(msg.status, ShouldEqual, Syncing)
  163. msg = <-managerChan
  164. So(msg.status, ShouldEqual, Success)
  165. expectedOutput := fmt.Sprintf(
  166. "%s\n%s\n",
  167. provider.WorkingDir(), provider.WorkingDir(),
  168. )
  169. loggedContent, err := ioutil.ReadFile(provider.LogFile())
  170. So(err, ShouldBeNil)
  171. So(string(loggedContent), ShouldEqual, expectedOutput)
  172. job.ctrlChan <- jobDisable
  173. <-job.disabled
  174. })
  175. Convey("If we disable it", func(ctx C) {
  176. go job.Run(managerChan, semaphore)
  177. job.ctrlChan <- jobStart
  178. msg := <-managerChan
  179. So(msg.status, ShouldEqual, PreSyncing)
  180. msg = <-managerChan
  181. So(msg.status, ShouldEqual, Syncing)
  182. job.ctrlChan <- jobDisable
  183. msg = <-managerChan
  184. So(msg.status, ShouldEqual, Failed)
  185. So(msg.msg, ShouldEqual, "killed by manager")
  186. <-job.disabled
  187. })
  188. Convey("If we stop it twice, than start it", func(ctx C) {
  189. go job.Run(managerChan, semaphore)
  190. job.ctrlChan <- jobStart
  191. msg := <-managerChan
  192. So(msg.status, ShouldEqual, PreSyncing)
  193. msg = <-managerChan
  194. So(msg.status, ShouldEqual, Syncing)
  195. job.ctrlChan <- jobStop
  196. msg = <-managerChan
  197. So(msg.status, ShouldEqual, Failed)
  198. So(msg.msg, ShouldEqual, "killed by manager")
  199. job.ctrlChan <- jobStop // should be ignored
  200. job.ctrlChan <- jobStart
  201. msg = <-managerChan
  202. So(msg.status, ShouldEqual, PreSyncing)
  203. msg = <-managerChan
  204. So(msg.status, ShouldEqual, Syncing)
  205. msg = <-managerChan
  206. So(msg.status, ShouldEqual, Success)
  207. expectedOutput := fmt.Sprintf(
  208. "%s\n%s\n",
  209. provider.WorkingDir(), provider.WorkingDir(),
  210. )
  211. loggedContent, err := ioutil.ReadFile(provider.LogFile())
  212. So(err, ShouldBeNil)
  213. So(string(loggedContent), ShouldEqual, expectedOutput)
  214. job.ctrlChan <- jobDisable
  215. <-job.disabled
  216. })
  217. })
  218. })
  219. }