github.com/adacta-ru/mattermost-server/v5@v5.31.1/jobs/active_users/worker.go (about)

     1  // Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
     2  // See LICENSE.txt for license information.
     3  
     4  package active_users
     5  
     6  import (
     7  	"net/http"
     8  
     9  	"github.com/adacta-ru/mattermost-server/v5/app"
    10  	"github.com/adacta-ru/mattermost-server/v5/jobs"
    11  	tjobs "github.com/adacta-ru/mattermost-server/v5/jobs/interfaces"
    12  	"github.com/adacta-ru/mattermost-server/v5/mlog"
    13  	"github.com/adacta-ru/mattermost-server/v5/model"
    14  )
    15  
    16  const (
    17  	JobName = "ActiveUsers"
    18  )
    19  
    20  type Worker struct {
    21  	name      string
    22  	stop      chan bool
    23  	stopped   chan bool
    24  	jobs      chan model.Job
    25  	jobServer *jobs.JobServer
    26  	app       *app.App
    27  }
    28  
    29  func init() {
    30  	app.RegisterJobsActiveUsersInterface(func(a *app.App) tjobs.ActiveUsersJobInterface {
    31  		return &ActiveUsersJobInterfaceImpl{a}
    32  	})
    33  }
    34  
    35  type ActiveUsersJobInterfaceImpl struct {
    36  	App *app.App
    37  }
    38  
    39  func (m *ActiveUsersJobInterfaceImpl) MakeWorker() model.Worker {
    40  	worker := Worker{
    41  		name:      JobName,
    42  		stop:      make(chan bool, 1),
    43  		stopped:   make(chan bool, 1),
    44  		jobs:      make(chan model.Job),
    45  		jobServer: m.App.Srv().Jobs,
    46  		app:       m.App,
    47  	}
    48  	return &worker
    49  }
    50  
    51  func (worker *Worker) Run() {
    52  	mlog.Debug("Worker started", mlog.String("worker", worker.name))
    53  
    54  	defer func() {
    55  		mlog.Debug("Worker finished", mlog.String("worker", worker.name))
    56  		worker.stopped <- true
    57  	}()
    58  
    59  	for {
    60  		select {
    61  		case <-worker.stop:
    62  			mlog.Debug("Worker received stop signal", mlog.String("worker", worker.name))
    63  			return
    64  		case job := <-worker.jobs:
    65  			mlog.Debug("Worker received a new candidate job.", mlog.String("worker", worker.name))
    66  			worker.DoJob(&job)
    67  		}
    68  	}
    69  }
    70  
    71  func (worker *Worker) Stop() {
    72  	mlog.Debug("Worker stopping", mlog.String("worker", worker.name))
    73  	worker.stop <- true
    74  	<-worker.stopped
    75  }
    76  
    77  func (worker *Worker) JobChannel() chan<- model.Job {
    78  	return worker.jobs
    79  }
    80  
    81  func (worker *Worker) DoJob(job *model.Job) {
    82  	if claimed, err := worker.jobServer.ClaimJob(job); err != nil {
    83  		mlog.Warn("Worker experienced an error while trying to claim job",
    84  			mlog.String("worker", worker.name),
    85  			mlog.String("job_id", job.Id),
    86  			mlog.String("error", err.Error()))
    87  		return
    88  	} else if !claimed {
    89  		return
    90  	}
    91  
    92  	count, err := worker.app.Srv().Store.User().Count(model.UserCountOptions{IncludeDeleted: false})
    93  
    94  	if err != nil {
    95  		mlog.Error("Worker: Failed to get active user count", mlog.String("worker", worker.name), mlog.String("job_id", job.Id), mlog.String("error", err.Error()))
    96  		worker.setJobError(job, model.NewAppError("DoJob", "app.user.get_total_users_count.app_error", nil, err.Error(), http.StatusInternalServerError))
    97  		return
    98  	}
    99  
   100  	if worker.app.Metrics() != nil {
   101  		worker.app.Metrics().ObserveEnabledUsers(count)
   102  	}
   103  
   104  	mlog.Info("Worker: Job is complete", mlog.String("worker", worker.name), mlog.String("job_id", job.Id))
   105  	worker.setJobSuccess(job)
   106  }
   107  
   108  func (worker *Worker) setJobSuccess(job *model.Job) {
   109  	if err := worker.app.Srv().Jobs.SetJobSuccess(job); err != nil {
   110  		mlog.Error("Worker: Failed to set success for job", mlog.String("worker", worker.name), mlog.String("job_id", job.Id), mlog.String("error", err.Error()))
   111  		worker.setJobError(job, err)
   112  	}
   113  }
   114  
   115  func (worker *Worker) setJobError(job *model.Job, appError *model.AppError) {
   116  	if err := worker.app.Srv().Jobs.SetJobError(job, appError); err != nil {
   117  		mlog.Error("Worker: Failed to set job error", mlog.String("worker", worker.name), mlog.String("job_id", job.Id), mlog.String("error", err.Error()))
   118  	}
   119  }