/
main.go
151 lines (128 loc) · 3.26 KB
/
main.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
package main
/*
Simple command line beanstalkd client
Allows two modes of operation: push and pull.
Push: Reads from stdin pipe and writes it to the specified beanstalkd tube
Pull: Blocks and reserves a job from beanstalkd. Once read, it deletes the
job from the specified tube.
Push supports the -m option. Setting this will cause beanc to process each
line on STDIN as a seperate job rather than as one whole job (the default)
*/
import (
"flag"
"fmt"
"github.com/iwanbk/gobeanstalk"
"io/ioutil"
"log"
"os"
"strings"
)
var (
version *bool = flag.Bool("version", false, "The version number")
verbose *bool = flag.Bool("v", false, "Verbosity")
multiline *bool = flag.Bool("m", false, "Creates a new job for each line")
host *string = flag.String("host", "127.0.0.1:11300", "The host address and port")
tube *string = flag.String("tube", "default", "The tube to use or watch, depending on the action")
pri *int = flag.Int("pri", 0, "The job priority, used when pushing")
delay *int = flag.Int("delay", 0, "The job delay, used when pushing")
ttr *int = flag.Int("ttr", 10, "The job ttr, used when pushing")
)
func main() {
log.SetFlags(log.Lshortfile)
log.SetPrefix("beanc:")
flag.Parse()
if *version {
fmt.Printf("%d.%d\n", VERSION_MAJOR, VERSION_MINOR)
os.Exit(1)
}
if *verbose {
fmt.Println("Verbose")
}
conn, err := gobeanstalk.Dial(*host)
if err != nil {
log.Printf("connect failed")
log.Fatal(err)
}
switch flag.Arg(0) {
case "push":
pushCommand(conn)
case "pull":
pullCommand(conn)
default:
log.Println("Unrecognised command")
os.Exit(-1)
}
os.Exit(0)
}
func pushCommand(conn *gobeanstalk.Conn) {
if *tube != "" {
err := conn.Use(*tube)
if err != nil {
log.Printf("Use %s failed\n", *tube)
log.Fatal(err)
}
}
data, err := ioutil.ReadAll(os.Stdin)
if err != nil {
log.Println("Stdin read error")
log.Fatal(err)
}
if len(data) < 1 {
log.Println("Stdin has no data")
log.Fatal()
}
if *verbose {
fmt.Println(string(data))
}
var dataset []string
if *multiline == true {
dataset = strings.Split(string(data), "\n")
} else {
dataset = append(dataset, string(data))
}
for _, job := range dataset {
if len(job) == 0 { // Skip blank lines
continue
}
_, err = conn.Put([]byte(job), *pri, *delay, *ttr)
if err != nil {
log.Println("Put failed")
log.Fatal(err)
}
}
}
func pullCommand(conn *gobeanstalk.Conn) {
var tubesToWatch []string = strings.SplitN(*tube, ",", -1)
var watchDefault bool = false
for _, tubeName := range tubesToWatch {
_, err := conn.Watch(tubeName)
if err != nil {
log.Printf("Watch %s failed\n", tubeName)
log.Fatal(err)
}
if tubeName == "default" {
watchDefault = true
}
}
// As beanstalk by default adds the tube 'default' to the
// connections watch list, we need to remove it from this
// connections watch list.
if watchDefault == false {
_, err := conn.Ignore("default")
if err != nil {
log.Print("Ignore 'default' tube failed\n")
log.Fatal(err)
}
}
j, err := conn.Reserve()
if err != nil {
log.Println("Reserve failed")
log.Fatal(err)
}
err = conn.Delete(j.Id)
if err != nil {
log.Printf("Delete failed. Job ID: %d\n", j.Id)
log.Fatal(err)
}
os.Stdout.Write(j.Body)
}