Job服务孵化


业务处理中,我们会有编写各种脚本任务的需求,如定时、周期、守护等类型的job,
其实编写任务脚本在流程上是比较标准化的:

  • 接受命令行参数 -> 解析命令 -> 选择job -> 执行 -> 记录结果

由此,为了避免这种枯燥重复的工作,我们提供了Job孵化功能,当然目前功能还比较基础,也希望大家多提宝贵意见,共同完善!

接入

使用 rigger 脚手架自动生成

  1. [developer@localhost rigger]$ rigger new job myJob
  2. 正克隆到 '/tmp/myJob'...
  3. myJob Job server 已生成!

rigger new job 是命令, myJob 是管理器的文件夹名称,上述命令会在当前目录下生成子目录myJob

目录结构

  1. ./myJob
  2. -jobsMap.go #注册jobs
  3. -main.go #job运行主入口

编译

两种方式:

  1. 在主服务的Makefile 中增加编译命令
  2. 直接编译
  1. //执行如下命令会生成可执行文件 myJob
  2. $ cd myJob && go build ./

注册Job

myJob/jobsMap.go 中添加, 具体任务可以直接写在此处,也可以引入其他包

jobFuncs的 key 为任务标识

  1. func initFuncMap() {
  2. //example
  3. jobFuncs["testJob"] = clijob.Job{
  4. Name: "testJob",
  5. Task: func() error {
  6. for i := 0; i < 10; i++ {
  7. fmt.Println("testJob")
  8. time.Sleep(time.Second)
  9. }
  10. return nil
  11. },
  12. }
  13. jobFuncs["testJob2"] = clijob.Job{
  14. Name: "testJob2",
  15. Task: func() error {
  16. for i := 0; i < 10; i++ {
  17. fmt.Println("testJob2")
  18. time.Sleep(time.Second)
  19. }
  20. return nil
  21. },
  22. }
  23. }

执行已注册任务

查看job的命令选项

  1. [developer@localhost myJob]$ ./myJob -h
  2. Usage of ./myJob:
  3. -c string
  4. config path
  5. -cfg string
  6. json config path (default "conf/config.json")
  7. -extended string
  8. extended options, You can customize the options to bypass the flag.parse() restrictions
  9. -f foreground
  10. -m mock
  11. -mode int
  12. mode
  13. -p string
  14. config path prefix with no trailing backslash
  15. -s string
  16. start or stop
  17. -usr1 string
  18. user defined flag -usr1
  19. -usr2 string
  20. user defined flag -usr2
  21. -usr3 string
  22. user defined flag -usr3
  23. -usr4 string
  24. user defined flag -usr4
  25. -usr5 string
  26. user defined flag -usr5
  27. -v version

其中Job管理器的默认把-extended作为解析对象,其值代表任务函数的标识。

选择任务testJob并执行

  1. $./myJob -extended testJob
  2. testJob
  3. [16:42:29 CST 2019/12/19] [INFO] (server.go:116:561420000000010 localhost.localdomain) doJob [start],任务主入口
  4. [16:42:29 CST 2019/12/19] [INFO] (server.go:116:561420000000011 localhost.localdomain) doJob [start],任务:testJob
  5. testJob
  6. testJob
  7. testJob
  8. testJob
  9. testJob
  10. testJob
  11. testJob
  12. testJob
  13. testJob
  14. [16:42:39 CST 2019/12/19] [INFO] (server.go:118:561420000000011 localhost.localdomain) doJob [end],任务:testJob
  15. [16:42:39 CST 2019/12/19] [INFO] (server.go:118:561420000000010 localhost.localdomain) doJob [end],任务主入口
  16. [16:42:39 CST 2019/12/19] [INFO] (server.go:63:561420000000010 localhost.localdomain) Stop 正在退出...

自定义命令行参数解析

简单修改下myJob/main.go

  1. package main
  2. import (
  3. "fmt"
  4. "github.com/tal-tech/hera/clijob"
  5. logger "github.com/tal-tech/xesLogger"
  6. "github.com/tal-tech/xesTools/flagutil"
  7. )
  8. func main() {
  9. //添加自定义命令行解析器
  10. job := clijob.NewJobServer(clijob.OptSetCmdParser(&MyParser{}))
  11. job.AddJobs(GetFuncs())
  12. err := job.Start()
  13. if err != nil {
  14. fmt.Println("err:", err)
  15. }
  16. }
  17. //-----------------------自定义命令行解析器---------------------------
  18. type MyParser struct {
  19. }
  20. //为了演示自定义命令行参数解析器的用法, 此处复制了一份默认的写法
  21. func (p *MyParser) JobArgParse(jobs map[string]clijob.Job) (selectedJobs []clijob.Job, err error) {
  22. fmt.Println("自定义解析器")
  23. cmdArg := *flagutil.GetExtendedopt()
  24. job, ok := jobs[cmdArg]
  25. if !ok {
  26. return nil, logger.NewError("[ " + cmdArg + " ]任务未定义")
  27. }
  28. selectedJobs = make([]clijob.Job, 0, 1)
  29. selectedJobs = append(selectedJobs, job)
  30. return selectedJobs, nil
  31. }