解决循环依赖
parent
f39d0ac508
commit
b0909706ec
|
@ -26,3 +26,4 @@ _testmain.go
|
||||||
.idea
|
.idea
|
||||||
data/*
|
data/*
|
||||||
log/*
|
log/*
|
||||||
|
conf/install.lock
|
||||||
|
|
10
cmd/web.go
10
cmd/web.go
|
@ -6,9 +6,7 @@ import (
|
||||||
"github.com/go-macaron/gzip"
|
"github.com/go-macaron/gzip"
|
||||||
"github.com/go-macaron/session"
|
"github.com/go-macaron/session"
|
||||||
"github.com/go-macaron/csrf"
|
"github.com/go-macaron/csrf"
|
||||||
"scheduler/utils"
|
"scheduler/modules/app"
|
||||||
"fmt"
|
|
||||||
"scheduler/utils/app"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// web服务器默认端口
|
// web服务器默认端口
|
||||||
|
@ -31,7 +29,7 @@ var CmdWeb = cli.Command{
|
||||||
|
|
||||||
func run(ctx *cli.Context) {
|
func run(ctx *cli.Context) {
|
||||||
// 检测环境
|
// 检测环境
|
||||||
utils.CheckEnv()
|
app.CheckEnv()
|
||||||
// 启动定时任务
|
// 启动定时任务
|
||||||
runScheduler()
|
runScheduler()
|
||||||
m := macaron.Classic()
|
m := macaron.Classic()
|
||||||
|
@ -44,7 +42,9 @@ func run(ctx *cli.Context) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// 定时任务调度
|
// 定时任务调度
|
||||||
func runScheduler() {}
|
func runScheduler() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
// 路由注册
|
// 路由注册
|
||||||
func registerRouter(m *macaron.Macaron) {
|
func registerRouter(m *macaron.Macaron) {
|
||||||
|
|
|
@ -1,8 +0,0 @@
|
||||||
[db]
|
|
||||||
password = wozaixiamen
|
|
||||||
charset = utf8
|
|
||||||
database = cron
|
|
||||||
host = 127.0.0.1
|
|
||||||
port = 3306
|
|
||||||
user = root
|
|
||||||
prefix =
|
|
|
@ -1,5 +1,6 @@
|
||||||
package models
|
package models
|
||||||
|
|
||||||
|
|
||||||
// 主机
|
// 主机
|
||||||
type Host struct {
|
type Host struct {
|
||||||
Id int16 `xorm:"smallint pk autoincr"`
|
Id int16 `xorm:"smallint pk autoincr"`
|
||||||
|
|
|
@ -3,24 +3,17 @@ package models
|
||||||
import (
|
import (
|
||||||
"github.com/go-xorm/xorm"
|
"github.com/go-xorm/xorm"
|
||||||
"fmt"
|
"fmt"
|
||||||
"scheduler/utils/setting"
|
"scheduler/modules/setting"
|
||||||
"github.com/go-xorm/core"
|
"github.com/go-xorm/core"
|
||||||
_ "github.com/go-sql-driver/mysql"
|
_ "github.com/go-sql-driver/mysql"
|
||||||
"gopkg.in/macaron.v1"
|
"gopkg.in/macaron.v1"
|
||||||
"scheduler/utils/app"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var Db *xorm.Engine
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
if app.Installed {
|
|
||||||
Db = createDb()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
type Status int8
|
type Status int8
|
||||||
type CommonMap map[string]interface{}
|
type CommonMap map[string]interface{}
|
||||||
|
|
||||||
|
var Db *xorm.Engine
|
||||||
|
|
||||||
const (
|
const (
|
||||||
Disabled Status = 0 // 禁用
|
Disabled Status = 0 // 禁用
|
||||||
Failure Status = 0 // 失败
|
Failure Status = 0 // 失败
|
||||||
|
@ -36,8 +29,8 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
// 创建Db
|
// 创建Db
|
||||||
func createDb() *xorm.Engine{
|
func CreateDb(configFile string) *xorm.Engine{
|
||||||
config,err := setting.Read()
|
config,err := setting.Read(configFile)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
package models
|
package models
|
||||||
|
|
||||||
import "time"
|
import (
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
type TaskLog struct{
|
type TaskLog struct{
|
||||||
Id int `xorm:"pk autoincr"`
|
Id int `xorm:"pk autoincr"`
|
||||||
|
|
|
@ -2,7 +2,7 @@ package models
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"time"
|
"time"
|
||||||
"scheduler/utils"
|
"scheduler/modules/utils"
|
||||||
)
|
)
|
||||||
|
|
||||||
const PasswordSaltLength = 6;
|
const PasswordSaltLength = 6;
|
||||||
|
|
|
@ -4,18 +4,12 @@ package ansible
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"os"
|
"os"
|
||||||
"scheduler/utils"
|
"scheduler/modules/utils"
|
||||||
"errors"
|
"errors"
|
||||||
"gopkg.in/yaml.v2"
|
"gopkg.in/yaml.v2"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"scheduler/utils/app"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
|
||||||
// ansible配置文件目录
|
|
||||||
os.Setenv("ANSIBLE_CONFIG", app.ConfDir)
|
|
||||||
}
|
|
||||||
|
|
||||||
type Handler map[string]interface{}
|
type Handler map[string]interface{}
|
||||||
|
|
||||||
type Playbook struct {
|
type Playbook struct {
|
|
@ -0,0 +1,95 @@
|
||||||
|
package app
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"scheduler/modules/crontask"
|
||||||
|
"scheduler/models"
|
||||||
|
"runtime"
|
||||||
|
"scheduler/modules/utils"
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
AppDir string // 应用根目录
|
||||||
|
ConfDir string // 配置目录
|
||||||
|
LogDir string // 日志目录
|
||||||
|
DataDir string // 数据目录,存放session文件等
|
||||||
|
AppConfig string // 应用配置文件
|
||||||
|
Installed bool // 应用是否安装过
|
||||||
|
CronTask crontask.CronTask // 定时任务
|
||||||
|
)
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
wd, err := os.Getwd()
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
AppDir = wd
|
||||||
|
ConfDir = AppDir + "/conf"
|
||||||
|
LogDir = AppDir + "/log"
|
||||||
|
DataDir = AppDir + "/data"
|
||||||
|
AppConfig = AppDir + "/app.ini"
|
||||||
|
checkDirExists(ConfDir, LogDir, DataDir)
|
||||||
|
// ansible配置文件目录
|
||||||
|
os.Setenv("ANSIBLE_CONFIG", ConfDir)
|
||||||
|
Installed = IsInstalled()
|
||||||
|
if Installed {
|
||||||
|
initResource()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 判断应用是否安装过
|
||||||
|
func IsInstalled() bool {
|
||||||
|
_, err := os.Stat(ConfDir + "/install.lock")
|
||||||
|
if os.IsNotExist(err) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// 检测环境
|
||||||
|
func CheckEnv() {
|
||||||
|
// ansible不支持安装在windows上, windows只能作为被控机
|
||||||
|
if runtime.GOOS == "windows" {
|
||||||
|
panic("不支持在windows上运行")
|
||||||
|
}
|
||||||
|
_, err := utils.ExecShell("ansible", "--version")
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
_, err = utils.ExecShell("ansible-playbook", "--version")
|
||||||
|
if err != nil {
|
||||||
|
panic("ansible-playbook not found")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 创建安装锁文件
|
||||||
|
func CreateInstallLock() error {
|
||||||
|
_, err := os.Create(ConfDir + "/install.lock")
|
||||||
|
if err != nil {
|
||||||
|
utils.RecordLog("创建安装锁文件失败")
|
||||||
|
}
|
||||||
|
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// 初始化资源
|
||||||
|
func initResource() {
|
||||||
|
crontask.DefaultCronTask = crontask.CreateCronTask()
|
||||||
|
|
||||||
|
models.Db = models.CreateDb(AppConfig)
|
||||||
|
}
|
||||||
|
|
||||||
|
// 检测目录是否存在
|
||||||
|
func checkDirExists(path... string) {
|
||||||
|
for _, value := range(path) {
|
||||||
|
_, err := os.Stat(value)
|
||||||
|
if os.IsNotExist(err) {
|
||||||
|
panic(value + "目录不存在")
|
||||||
|
}
|
||||||
|
if os.IsPermission(err) {
|
||||||
|
panic(value + "目录无权限操作")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,25 +1,22 @@
|
||||||
package utils
|
package crontask
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/robfig/cron"
|
"github.com/robfig/cron"
|
||||||
"errors"
|
"errors"
|
||||||
"scheduler/utils/app"
|
|
||||||
"sync"
|
"sync"
|
||||||
)
|
)
|
||||||
|
|
||||||
var DefaultCronTask CronTask;
|
var DefaultCronTask *CronTask
|
||||||
|
|
||||||
type CronTask struct {
|
type CronTask struct {
|
||||||
sync.RWMutex
|
sync.RWMutex
|
||||||
tasks map[string]*cron.Cron
|
tasks map[string]*cron.Cron
|
||||||
}
|
}
|
||||||
|
|
||||||
func init() {
|
func CreateCronTask() *CronTask {
|
||||||
if app.Installed {
|
return &CronTask {
|
||||||
DefaultCronTask = CronTask{
|
sync.RWMutex{},
|
||||||
sync.RWMutex{},
|
make(map[string]*cron.Cron),
|
||||||
make(map[string]*cron.Cron),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,12 +3,11 @@ package setting
|
||||||
import (
|
import (
|
||||||
"gopkg.in/ini.v1"
|
"gopkg.in/ini.v1"
|
||||||
"errors"
|
"errors"
|
||||||
"scheduler/utils/app"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// 读取配置
|
// 读取配置
|
||||||
func Read() (config *ini.File, err error) {
|
func Read(filename string) (config *ini.File, err error) {
|
||||||
config, err = ini.Load(app.AppConfig)
|
config, err = ini.Load(filename)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -18,7 +17,7 @@ func Read() (config *ini.File, err error) {
|
||||||
|
|
||||||
|
|
||||||
// 写入配置
|
// 写入配置
|
||||||
func Write(config map[string]map[string]string) (error) {
|
func Write(config map[string]map[string]string, filename string) (error) {
|
||||||
if len(config) == 0 {
|
if len(config) == 0 {
|
||||||
return errors.New("参数不能为空")
|
return errors.New("参数不能为空")
|
||||||
}
|
}
|
||||||
|
@ -39,7 +38,7 @@ func Write(config map[string]map[string]string) (error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
err := file.SaveTo(app.AppConfig)
|
err := file.SaveTo(filename)
|
||||||
|
|
||||||
return err
|
return err
|
||||||
}
|
}
|
|
@ -7,34 +7,8 @@ import (
|
||||||
"crypto/md5"
|
"crypto/md5"
|
||||||
"encoding/hex"
|
"encoding/hex"
|
||||||
"log"
|
"log"
|
||||||
"os"
|
|
||||||
"runtime"
|
|
||||||
"scheduler/utils/app"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// 检测环境
|
|
||||||
func CheckEnv() {
|
|
||||||
// ansible不支持安装在windows上, windows只能作为被控机
|
|
||||||
if runtime.GOOS == "windows" {
|
|
||||||
panic("不支持在windows上运行")
|
|
||||||
}
|
|
||||||
_, err := ExecShell("ansible", "--version")
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
_, err = ExecShell("ansible-playbook", "--version")
|
|
||||||
if err != nil {
|
|
||||||
panic("ansible-playbook not found")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 创建安装锁文件
|
|
||||||
func CreateInstallLock() {
|
|
||||||
_, err := os.Create(app.ConfDir + "/install.lock")
|
|
||||||
if err != nil {
|
|
||||||
RecordLog("创建安装锁文件失败")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 执行shell命令
|
// 执行shell命令
|
||||||
func ExecShell(command string, args... string) (string, error) {
|
func ExecShell(command string, args... string) (string, error) {
|
|
@ -1,9 +1,9 @@
|
||||||
package main
|
package main
|
||||||
|
|
||||||
/*--------------------------------------------------------
|
/*--------------------------------------------------------
|
||||||
| 定时任务调度 |
|
定时任务调度
|
||||||
| 兼容Linux crontab时间格式语法,最小粒度可精确到每秒 |
|
兼容Linux crontab时间格式语法,最小粒度可精确到每秒
|
||||||
| 支持通过HTTP、SSH协议触发任务执行 |
|
支持通过HTTP、SSH协议触发任务执行
|
||||||
--------------------------------------------------------*/
|
--------------------------------------------------------*/
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
|
@ -2,29 +2,14 @@ package service
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"scheduler/models"
|
"scheduler/models"
|
||||||
"scheduler/utils"
|
"scheduler/modules/utils"
|
||||||
"net/http"
|
"net/http"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"strconv"
|
"strconv"
|
||||||
"time"
|
"time"
|
||||||
|
"scheduler/modules/crontask"
|
||||||
)
|
)
|
||||||
|
|
||||||
func initHosts() []models.Host {
|
|
||||||
// 获取所有主机
|
|
||||||
hostModel := new(models.Host)
|
|
||||||
list, err := hostModel.List()
|
|
||||||
if err != nil {
|
|
||||||
utils.RecordLog("获取主机列表失败-", err.Error())
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
if len(list) == 0 {
|
|
||||||
utils.RecordLog("主机列表为空")
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
return list
|
|
||||||
}
|
|
||||||
|
|
||||||
type Task struct {}
|
type Task struct {}
|
||||||
|
|
||||||
// 初始化任务,从数据库取出所有任务添加到定时任务
|
// 初始化任务,从数据库取出所有任务添加到定时任务
|
||||||
|
@ -60,7 +45,7 @@ func(task *Task) Add(taskModel models.Task) {
|
||||||
utils.RecordLog("任务协议不存在-协议编号: ", taskModel.Protocol)
|
utils.RecordLog("任务协议不存在-协议编号: ", taskModel.Protocol)
|
||||||
}
|
}
|
||||||
if (taskFunc != nil) {
|
if (taskFunc != nil) {
|
||||||
utils.DefaultCronTask.Add(strconv.Itoa(taskModel.Id), taskModel.Spec, taskFunc)
|
crontask.DefaultCronTask.Add(strconv.Itoa(taskModel.Id), taskModel.Spec, taskFunc)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -109,4 +94,6 @@ func(h *HTTPHandler) Run(taskModel models.Task) {
|
||||||
type SSHHandler struct {}
|
type SSHHandler struct {}
|
||||||
|
|
||||||
// 执行SSH任务
|
// 执行SSH任务
|
||||||
func(ssh *SSHHandler) Run(taskModel models.Task) {}
|
func(ssh *SSHHandler) Run(taskModel models.Task) {
|
||||||
|
|
||||||
|
}
|
|
@ -1,51 +0,0 @@
|
||||||
package app
|
|
||||||
|
|
||||||
import (
|
|
||||||
"os"
|
|
||||||
)
|
|
||||||
|
|
||||||
var (
|
|
||||||
AppDir string // 应用根目录
|
|
||||||
ConfDir string // 配置目录
|
|
||||||
LogDir string // 日志目录
|
|
||||||
DataDir string // 数据目录,存放session文件等
|
|
||||||
AppConfig string // 应用配置文件
|
|
||||||
Installed bool // 应用是否安装过
|
|
||||||
)
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
wd, err := os.Getwd()
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
AppDir = wd
|
|
||||||
ConfDir = AppDir + "/conf"
|
|
||||||
LogDir = AppDir + "/log"
|
|
||||||
DataDir = AppDir + "/data"
|
|
||||||
AppConfig = AppDir + "/app.ini"
|
|
||||||
checkDirExists(ConfDir, LogDir, DataDir)
|
|
||||||
Installed = isInstalled()
|
|
||||||
}
|
|
||||||
|
|
||||||
// 判断应用是否安装过
|
|
||||||
func isInstalled() bool {
|
|
||||||
_, err := os.Stat(ConfDir + "/install.lock")
|
|
||||||
if os.IsExist(err) {
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
// 检测目录是否存在
|
|
||||||
func checkDirExists(path... string) {
|
|
||||||
for _, value := range(path) {
|
|
||||||
_, err := os.Stat(value)
|
|
||||||
if os.IsNotExist(err) {
|
|
||||||
panic(value + "目录不存在")
|
|
||||||
}
|
|
||||||
if os.IsPermission(err) {
|
|
||||||
panic(value + "目录无权限操作")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
Loading…
Reference in New Issue