github.com/levb/mattermost-server@v5.3.1+incompatible/jobs/jobs_watcher.go (about) 1 // Copyright (c) 2017-present Mattermost, Inc. All Rights Reserved. 2 // See License.txt for license information. 3 4 package jobs 5 6 import ( 7 "fmt" 8 "math/rand" 9 "time" 10 11 "github.com/mattermost/mattermost-server/mlog" 12 "github.com/mattermost/mattermost-server/model" 13 ) 14 15 // Default polling interval for jobs termination. 16 // (Defining as `var` rather than `const` allows tests to lower the interval.) 17 var DEFAULT_WATCHER_POLLING_INTERVAL = 15000 18 19 type Watcher struct { 20 srv *JobServer 21 workers *Workers 22 23 stop chan bool 24 stopped chan bool 25 pollingInterval int 26 } 27 28 func (srv *JobServer) MakeWatcher(workers *Workers, pollingInterval int) *Watcher { 29 return &Watcher{ 30 stop: make(chan bool, 1), 31 stopped: make(chan bool, 1), 32 pollingInterval: pollingInterval, 33 workers: workers, 34 srv: srv, 35 } 36 } 37 38 func (watcher *Watcher) Start() { 39 mlog.Debug("Watcher Started") 40 41 // Delay for some random number of milliseconds before starting to ensure that multiple 42 // instances of the jobserver don't poll at a time too close to each other. 43 rand.Seed(time.Now().UTC().UnixNano()) 44 <-time.After(time.Duration(rand.Intn(watcher.pollingInterval)) * time.Millisecond) 45 46 defer func() { 47 mlog.Debug("Watcher Finished") 48 watcher.stopped <- true 49 }() 50 51 for { 52 select { 53 case <-watcher.stop: 54 mlog.Debug("Watcher: Received stop signal") 55 return 56 case <-time.After(time.Duration(watcher.pollingInterval) * time.Millisecond): 57 watcher.PollAndNotify() 58 } 59 } 60 } 61 62 func (watcher *Watcher) Stop() { 63 mlog.Debug("Watcher Stopping") 64 watcher.stop <- true 65 <-watcher.stopped 66 } 67 68 func (watcher *Watcher) PollAndNotify() { 69 if result := <-watcher.srv.Store.Job().GetAllByStatus(model.JOB_STATUS_PENDING); result.Err != nil { 70 mlog.Error(fmt.Sprintf("Error occurred getting all pending statuses: %v", result.Err.Error())) 71 } else { 72 jobs := result.Data.([]*model.Job) 73 74 for _, job := range jobs { 75 if job.Type == model.JOB_TYPE_DATA_RETENTION { 76 if watcher.workers.DataRetention != nil { 77 select { 78 case watcher.workers.DataRetention.JobChannel() <- *job: 79 default: 80 } 81 } 82 } else if job.Type == model.JOB_TYPE_MESSAGE_EXPORT { 83 if watcher.workers.MessageExport != nil { 84 select { 85 case watcher.workers.MessageExport.JobChannel() <- *job: 86 default: 87 } 88 } 89 } else if job.Type == model.JOB_TYPE_ELASTICSEARCH_POST_INDEXING { 90 if watcher.workers.ElasticsearchIndexing != nil { 91 select { 92 case watcher.workers.ElasticsearchIndexing.JobChannel() <- *job: 93 default: 94 } 95 } 96 } else if job.Type == model.JOB_TYPE_ELASTICSEARCH_POST_AGGREGATION { 97 if watcher.workers.ElasticsearchAggregation != nil { 98 select { 99 case watcher.workers.ElasticsearchAggregation.JobChannel() <- *job: 100 default: 101 } 102 } 103 } else if job.Type == model.JOB_TYPE_LDAP_SYNC { 104 if watcher.workers.LdapSync != nil { 105 select { 106 case watcher.workers.LdapSync.JobChannel() <- *job: 107 default: 108 } 109 } 110 } else if job.Type == model.JOB_TYPE_MIGRATIONS { 111 if watcher.workers.Migrations != nil { 112 select { 113 case watcher.workers.Migrations.JobChannel() <- *job: 114 default: 115 } 116 } 117 } 118 } 119 } 120 }