Skip to content

Commit

Permalink
generate and recreate crontab
Browse files Browse the repository at this point in the history
  • Loading branch information
YuheiNakasaka committed Apr 14, 2018
1 parent 04dd16f commit a97caa4
Show file tree
Hide file tree
Showing 3 changed files with 94 additions and 1 deletion.
3 changes: 2 additions & 1 deletion README.md
Expand Up @@ -60,7 +60,8 @@ $ curl -XGET "http://localhost:1323/programs?offset=0&limit=1" | jq
- 各放送局のスクリプトでは`RecorderBase`のコマンド実装とそれを`recorder.Generate(rb RecorderBase)`に渡すだけみたいな実装だけに絞る
- これによって放送局が増えた時は`RecorderBase`のコマンド実装だけすれば基本的にはやることは終わりになるのでメンテしやすくなりそう
- [x] アップロードするスクリプト
- [ ] cron設定するプロセス
- [x] cron設定するプロセス
- crontabをclearして再生成する雑な作り。既存のcrontabを消すから危険。
- [x] typeのカラムを追加するか考慮する
- on airしてるかどうかのフラグとラジオ局を表すカラムを追加した
- [ ] 各種ミドルウェアが入った開発用docker-compose
Expand Down
9 changes: 9 additions & 0 deletions cmd/cli/cli.go
Expand Up @@ -5,6 +5,7 @@ import (
"log"
"os"

"github.com/YuheiNakasaka/radiorec/internal/cron"
"github.com/YuheiNakasaka/radiorec/internal/db"
"github.com/YuheiNakasaka/radiorec/internal/recorder/ag"
"github.com/YuheiNakasaka/radiorec/internal/recorder/radiko"
Expand Down Expand Up @@ -53,6 +54,14 @@ func main() {
}
},
},
{
Name: "cron",
Aliases: []string{"c"},
Usage: "Clear old crontab and recreate new crontab.",
Action: func(c *cli.Context) error {
return cron.Generate()
},
},
}

err := app.Run(os.Args)
Expand Down
83 changes: 83 additions & 0 deletions internal/cron/cron.go
@@ -0,0 +1,83 @@
package cron

import (
"fmt"
"os"
"os/exec"
"path/filepath"
"regexp"
"strconv"
"strings"

"github.com/YuheiNakasaka/radiorec/internal/db"
)

// convertStartTime : 時間と分を分解してmapに格納し返す
func convertStartTime(s string) map[string]string {
words := strings.Split(s, ":")
hour := words[0]
minute := words[1]

rep := regexp.MustCompile(`^0`)
formatedHour := rep.ReplaceAllString(hour, "")
formatedMinute := rep.ReplaceAllString(minute, "")

return map[string]string{
"hour": formatedHour,
"minute": formatedMinute,
}
}

// generateCronLine : 設定するcron行を生成する
func generateCronLine(programID int, dayOfWeek int, times map[string]string) map[string]string {
chdirCmd := "cd /var/www/radiorec/;"
stdoutCmd := ">> /var/log/cron.log 2>&1"
mainCmd := "/var/www/radiorec record -i " + strconv.Itoa(programID) + " -s s3"
cronTime := times["minute"] + " " + times["hour"] + " * * " + strconv.Itoa(dayOfWeek)

cmds := map[string]string{}
cmds["schedule"] = cronTime
cmds["exec"] = chdirCmd + mainCmd + " " + stdoutCmd

return cmds
}

// Generate creates cron settings
func Generate() error {
// get all records being on air.
mydb := &db.MyDB{}
err := mydb.New()
if err != nil {
return fmt.Errorf("Failed to connect database: %v", err)
}
conn := mydb.Connection
results := []db.Program{}
conn.Table("programs").
Select("*").
Where("programs.on_air_status = 1").
Order("programs.id").Scan(&results)

// create tmpfile to add crontab
tmpFilePath := filepath.Join(filepath.FromSlash("/tmp/new_crontab_lines"))
tmpfile, err := os.Create(tmpFilePath)
if err != nil {
return fmt.Errorf("Failed to create file: %v", err)
}
defer tmpfile.Close()
defer os.Remove(tmpFilePath)

// create cron lines
for _, result := range results {
time := convertStartTime(string(result.StartTime))
line := generateCronLine(result.ID, result.DayOfWeek, time)
if _, terr := tmpfile.WriteString(fmt.Sprintf("#%s\n%s\n", result.Name, line["schedule"]+" "+line["exec"])); terr != nil {
return fmt.Errorf("Failed to write line in crontab: %v", terr)
}
}

// redirect the lines to crontab
cmd := "crontab < " + tmpFilePath
exec.Command("sh", "-c", cmd).Run()

return err
}

0 comments on commit a97caa4

Please sign in to comment.