hotdog 0.30.0 → 0.31.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 704ccd17864c284a1daa3550e9c955469e718ee4
4
- data.tar.gz: 0d5e59e8c274f25ebd179e92123380c5336d7cec
3
+ metadata.gz: 9919088eda80ed6ec42ab4448a1e9474a8f6b3cf
4
+ data.tar.gz: b4659b72b4ee22337f1d74d14dad1d0d686b8bf0
5
5
  SHA512:
6
- metadata.gz: 03d9ceb9147a75449c9b7542f3deecdb331cd0736d902603101508fbd1ef87881c82503b223dcd2c710f5f69c8408b173b95b1a17c57bbb08b5ca27857bfcc14
7
- data.tar.gz: 5d32974bbbb07110a678538b5275ca792a1d76eb5ae086ad1b9831ff434d1937d4eae8f0ae4048df393bec2f81664223da444ba9aeee3467224b78bf4e0d375d
6
+ metadata.gz: 6cdebee0eaf5a3c347aa9fb8fae6f589467cf040edcad75d1d220d2b29a7842a7619f1b1149fe58bb1b116e6fc59ae248b48af5291655e03da4866ade02d1005
7
+ data.tar.gz: 9af471697553ce75493da82aedfa9f79c59f65de5a74407b7fbf626bc04571dcfb5e29be495021eecea48fd3814cecabf6abd87cb9f8abe3a36550a934f01868
@@ -51,7 +51,8 @@ module Hotdog
51
51
  force: false,
52
52
  format: "text",
53
53
  headers: false,
54
- status: STATUS_RUNNING,
54
+ source: nil,
55
+ status: nil,
55
56
  listing: false,
56
57
  logger: @logger,
57
58
  max_time: 5,
@@ -159,11 +160,21 @@ module Hotdog
159
160
  end
160
161
  end
161
162
 
163
+ def source()
164
+ options.fetch(:source, SOURCE_DATADOG)
165
+ end
166
+
167
+ def source_name(source=self.source)
168
+ {
169
+ SOURCE_DATADOG => "datadog",
170
+ }.fetch(source, "unknown")
171
+ end
172
+
162
173
  def status()
163
174
  options.fetch(:status, STATUS_RUNNING)
164
175
  end
165
176
 
166
- def status_name()
177
+ def status_name(status=self.status)
167
178
  {
168
179
  STATUS_PENDING => "pending",
169
180
  STATUS_RUNNING => "running",
@@ -171,7 +182,7 @@ module Hotdog
171
182
  STATUS_TERMINATED => "terminated",
172
183
  STATUS_STOPPING => "stopping",
173
184
  STATUS_STOPPED => "stopped",
174
- }.fetch(self.status, "unknown")
185
+ }.fetch(status, "unknown")
175
186
  end
176
187
 
177
188
  private
@@ -215,22 +226,38 @@ module Hotdog
215
226
  @optparse.on("-h", "--[no-]headers", "Display headeres for each columns") do |v|
216
227
  options[:headers] = v
217
228
  end
229
+ @optparse.on("--source=SOURCE", "Specify custom host source") do |v|
230
+ case v
231
+ when /\A\d\z/i
232
+ options[:source] = v.to_i
233
+ when /\A(?:all|any)\z/i
234
+ options[:source] = nil
235
+ when /\A(?:datadog)\z/i
236
+ options[:source] = SOURCE_DATADOG
237
+ else
238
+ raise(OptionParser::InvalidArgument.new("unknown source: #{v}"))
239
+ end
240
+ end
218
241
  @optparse.on("--status=STATUS", "Specify custom host status") do |v|
219
242
  case v
220
- when /\Apending\z/i
243
+ when /\A\d\z/i
244
+ options[:status] = v.to_i
245
+ when /\A(?:all|any)\z/i
246
+ options[:status] = nil
247
+ when /\A(?:pending)\z/i
221
248
  options[:status] = STATUS_PENDING
222
- when /\Arunning\z/i
249
+ when /\A(?:running)\z/i
223
250
  options[:status] = STATUS_RUNNING
224
- when /\Ashutting-down\z/i
251
+ when /\A(?:shutting-down)\z/i
225
252
  options[:status] = STATUS_SHUTTING_DOWN
226
- when /\Aterminated\z/i
253
+ when /\A(?:terminated)\z/i
227
254
  options[:status] = STATUS_TERMINATED
228
- when /\Astopping\z/i
255
+ when /\A(?:stopping)\z/i
229
256
  options[:status] = STATUS_STOPPING
230
- when /\Astopped\z/i
257
+ when /\A(?:stopped)\z/i
231
258
  options[:status] = STATUS_STOPPED
232
259
  else
233
- options[:status] = v.to_i
260
+ raise(OptionParser::InvalidArgument.new("unknown status: #{v}"))
234
261
  end
235
262
  end
236
263
  @optparse.on("-l", "--[no-]listing", "Use listing format") do |v|
@@ -60,9 +60,10 @@ module Hotdog
60
60
  @db.transaction do
61
61
  sqlite_limit_compound_select = options[:sqlite_limit_compound_select] || SQLITE_LIMIT_COMPOUND_SELECT
62
62
  hosts.each_slice(sqlite_limit_compound_select - 1) do |hosts|
63
- q = "UPDATE hosts SET status = ? WHERE name IN (%s);" % hosts.map { "?" }.join(", ")
64
- execute_db(@db, q, [STATUS_STOPPING] + hosts)
63
+ execute_db(@db, "DELETE FROM hosts_tags WHERE tag_id IN ( SELECT id FROM tags WHERE name = '@status' ) AND host_id IN ( SELECT id FROM hosts WHERE name IN (%s) );" % hosts.map { "?" }.join(", "), hosts)
64
+ execute_db(@db, "UPDATE hosts SET status = ? WHERE name IN (%s);" % hosts.map { "?" }.join(", "), [STATUS_STOPPING] + hosts)
65
65
  end
66
+ associate_tag_hosts(@db, "@status:#{application.status_name(STATUS_STOPPING)}", hosts)
66
67
  end
67
68
  end
68
69
  end
@@ -120,6 +120,14 @@ module Hotdog
120
120
  # return everything if given expression is empty
121
121
  expression = "*"
122
122
  end
123
+ if options[:source]
124
+ source_name = application.source_name(options[:source])
125
+ expression = "@source:#{source_name} AND (#{expression})"
126
+ end
127
+ if options[:status]
128
+ status_name = application.status_name(options[:status])
129
+ expression = "@status:#{status_name} AND (#{expression})"
130
+ end
123
131
  if options[:limit]
124
132
  expression = "LIMIT((#{expression}), #{options[:limit]})"
125
133
  end
@@ -15,6 +15,8 @@ module Hotdog
15
15
  default_option(options, :max_parallelism, Parallel.processor_count * 2)
16
16
  default_option(options, :shuffle, false)
17
17
  default_option(options, :ssh_config, nil)
18
+ # we must not need to run ssh against terminated hosts
19
+ default_option(options, :status, STATUS_RUNNING)
18
20
  optparse.on("-C", "Enable compression.") do |v|
19
21
  options[:ssh_options]["Compression"] = "yes"
20
22
  end
@@ -61,11 +61,7 @@ module Hotdog
61
61
 
62
62
  private
63
63
  def default_option(options, key, default_value)
64
- if options.key?(key)
65
- options[key]
66
- else
67
- options[key] = default_value
68
- end
64
+ options[key] = default_value
69
65
  end
70
66
 
71
67
  def prepare(db, query)
@@ -81,15 +77,6 @@ module Hotdog
81
77
  end
82
78
 
83
79
  def get_hosts(host_ids, tags=nil)
84
- status = application.status
85
- n = Array(host_ids).length
86
- host_ids = Array(host_ids).each_slice(SQLITE_LIMIT_COMPOUND_SELECT).flat_map { |host_ids|
87
- execute("SELECT id FROM hosts WHERE status = ? AND id IN (%s);" % host_ids.map { "?" }.join(", "), [status] + host_ids).map { |row| row[0] }
88
- }
89
- m = host_ids.length
90
- if n != m
91
- logger.warn("filtered out #{n - m} host(s) out of #{n} due to status != #{application.status_name}.")
92
- end
93
80
  tags ||= @options[:tags]
94
81
  update_db
95
82
  if host_ids.empty?
@@ -263,6 +250,7 @@ module Hotdog
263
250
  db = SQLite3::Database.new(persistent_db_path)
264
251
  copy_db(memory_db, db)
265
252
  close_db(memory_db)
253
+ $did_reload = true
266
254
  @db = db
267
255
  end
268
256
  end
@@ -295,6 +283,25 @@ module Hotdog
295
283
  execute_db(db, "CREATE TABLE IF NOT EXISTS hosts_tags (host_id INTEGER NOT NULL, tag_id INTEGER NOT NULL);")
296
284
  execute_db(db, "CREATE UNIQUE INDEX IF NOT EXISTS hosts_tags_host_id_tag_id ON hosts_tags (host_id, tag_id);")
297
285
 
286
+ execute_db(db, "CREATE TABLE IF NOT EXISTS source_names (id INTEGER PRIMARY KEY AUTOINCREMENT, name VARCHAR(200) NOT NULL COLLATE NOCASE);")
287
+ {
288
+ SOURCE_DATADOG => application.source_name(SOURCE_DATADOG),
289
+ }.each do |source_id, source_name|
290
+ execute_db(db, "INSERT OR IGNORE INTO source_names (id, name) VALUES (?, ?);", [source_id, source_name])
291
+ end
292
+
293
+ execute_db(db, "CREATE TABLE IF NOT EXISTS status_names (id INTEGER PRIMARY KEY AUTOINCREMENT, name VARCHAR(200) NOT NULL COLLATE NOCASE);")
294
+ {
295
+ STATUS_PENDING => application.status_name(STATUS_PENDING),
296
+ STATUS_RUNNING => application.status_name(STATUS_RUNNING),
297
+ STATUS_SHUTTING_DOWN => application.status_name(STATUS_SHUTTING_DOWN),
298
+ STATUS_TERMINATED => application.status_name(STATUS_TERMINATED),
299
+ STATUS_STOPPING => application.status_name(STATUS_STOPPING),
300
+ STATUS_STOPPED => application.status_name(STATUS_STOPPED),
301
+ }.each do |status_id, status_name|
302
+ execute_db(db, "INSERT OR IGNORE INTO status_names (id, name) VALUES (?, ?);", [status_id, status_name])
303
+ end
304
+
298
305
  known_tags = all_tags.keys.map { |tag| split_tag(tag) }.uniq
299
306
  create_tags(db, known_tags)
300
307
 
@@ -362,20 +369,48 @@ module Hotdog
362
369
  end
363
370
 
364
371
  def create_hosts(db, hosts, downtimes)
365
- hosts.each_slice(SQLITE_LIMIT_COMPOUND_SELECT / 2) do |hosts|
366
- q = "INSERT OR IGNORE INTO hosts (name, status) VALUES %s;" % hosts.map { "(?, ?)" }.join(", ")
372
+ hosts.each_slice(SQLITE_LIMIT_COMPOUND_SELECT / 3) do |hosts|
373
+ q = "INSERT OR IGNORE INTO hosts (name, source, status) VALUES %s;" % hosts.map { "(?, ?, ?)" }.join(", ")
367
374
  execute_db(db, q, hosts.map { |host|
375
+ source = SOURCE_DATADOG
368
376
  status = downtimes.include?(host) ? STATUS_STOPPED : STATUS_RUNNING
369
- [host, status]
377
+ [host, source, status]
370
378
  })
371
379
  end
380
+
372
381
  # create virtual `host` tag
373
382
  execute_db(db, "INSERT OR IGNORE INTO tags (name, value) SELECT 'host', hosts.name FROM hosts;")
374
- q = "INSERT OR REPLACE INTO hosts_tags (host_id, tag_id) " \
383
+ execute_db(db,
384
+ "INSERT OR REPLACE INTO hosts_tags (host_id, tag_id) " \
385
+ "SELECT hosts.id, tags.id FROM hosts " \
386
+ "INNER JOIN tags ON tags.name = 'host' AND hosts.name = tags.value;"
387
+ )
388
+
389
+ # create virtual `@host` tag
390
+ execute_db(db, "INSERT OR IGNORE INTO tags (name, value) SELECT '@host', hosts.name FROM hosts;")
391
+ execute_db(db,
392
+ "INSERT OR REPLACE INTO hosts_tags (host_id, tag_id) " \
393
+ "SELECT hosts.id, tags.id FROM hosts " \
394
+ "INNER JOIN tags ON tags.name = '@host' AND hosts.name = tags.value;"
395
+ )
396
+
397
+ # create virtual `@source` tag
398
+ execute_db(db, "INSERT OR IGNORE INTO tags (name, value) SELECT '@source', name FROM source_names;")
399
+ execute_db(db,
400
+ "INSERT OR REPLACE INTO hosts_tags (host_id, tag_id) " \
401
+ "SELECT hosts.id, tags.id FROM hosts " \
402
+ "INNER JOIN source_names ON hosts.source = source_names.id " \
403
+ "INNER JOIN tags ON tags.name = '@source' AND source_names.name = tags.value;"
404
+ )
405
+
406
+ # create virtual `@status` tag
407
+ execute_db(db, "INSERT OR IGNORE INTO tags (name, value) SELECT '@status', name FROM status_names;")
408
+ execute_db(db,
409
+ "INSERT OR REPLACE INTO hosts_tags (host_id, tag_id) " \
375
410
  "SELECT hosts.id, tags.id FROM hosts " \
376
- "INNER JOIN ( SELECT * FROM tags WHERE name = 'host' ) AS tags " \
377
- "ON hosts.name = tags.value;"
378
- execute_db(db, q)
411
+ "INNER JOIN status_names ON hosts.status = status_names.id " \
412
+ "INNER JOIN tags ON tags.name = '@status' AND status_names.name = tags.value;"
413
+ )
379
414
  end
380
415
 
381
416
  def create_tags(db, tags)
@@ -59,9 +59,13 @@ module Hotdog
59
59
  (min / (sqlite_limit_compound_select - 2)).upto(max / (sqlite_limit_compound_select - 2)).flat_map { |i|
60
60
  range = ((sqlite_limit_compound_select - 2) * i)...((sqlite_limit_compound_select - 2) * (i + 1))
61
61
  selected = values.select { |n| range === n }
62
- q = "SELECT id FROM hosts " \
63
- "WHERE ? <= id AND id < ? AND id NOT IN (%s);"
64
- environment.execute(q % selected.map { "?" }.join(", "), [range.first, range.last] + selected).map { |row| row.first }
62
+ if 0 < selected.length
63
+ q = "SELECT id FROM hosts " \
64
+ "WHERE ? <= id AND id < ? AND id NOT IN (%s);"
65
+ environment.execute(q % selected.map { "?" }.join(", "), [range.first, range.last] + selected).map { |row| row.first }
66
+ else
67
+ []
68
+ end
65
69
  }.tap do |values|
66
70
  environment.logger.debug("NOT expr: #{values.length} value(s)")
67
71
  end
@@ -201,9 +205,13 @@ module Hotdog
201
205
  range = (((sqlite_limit_compound_select - 2) / 2) * i)...(((sqlite_limit_compound_select - 2) / 2) * (i + 1))
202
206
  left_selected = left_values.select { |n| range === n }
203
207
  right_selected = right_values.select { |n| range === n }
204
- q = "SELECT id FROM hosts " \
205
- "WHERE ? <= id AND id < ? AND ( id IN (%s) AND id IN (%s) );"
206
- environment.execute(q % [left_selected.map { "?" }.join(", "), right_selected.map { "?" }.join(", ")], [range.first, range.last] + left_selected + right_selected).map { |row| row.first }
208
+ if 0 < left_selected.length and 0 < right_selected.length
209
+ q = "SELECT id FROM hosts " \
210
+ "WHERE ? <= id AND id < ? AND ( id IN (%s) AND id IN (%s) );"
211
+ environment.execute(q % [left_selected.map { "?" }.join(", "), right_selected.map { "?" }.join(", ")], [range.first, range.last] + left_selected + right_selected).map { |row| row.first }
212
+ else
213
+ []
214
+ end
207
215
  }.tap do |values|
208
216
  environment.logger.debug("lhs(#{left_values.length}) AND rhs(#{right_values.length}) => #{values.length}")
209
217
  end
@@ -106,9 +106,9 @@ module Hotdog
106
106
  )
107
107
  }
108
108
  rule(:tag) {
109
- ( regexp.as(:tagname_regexp) >> separator.as(:separator) >> regexp.as(:tagvalue_regexp) \
110
- | regexp.as(:tagname_regexp) >> separator.as(:separator) \
111
- | regexp.as(:tagname_regexp) \
109
+ ( tagname_regexp.as(:tagname_regexp) >> separator.as(:separator) >> tagvalue_regexp.as(:tagvalue_regexp) \
110
+ | tagname_regexp.as(:tagname_regexp) >> separator.as(:separator) \
111
+ | tagname_regexp.as(:tagname_regexp) \
112
112
  | tagname_glob.as(:tagname_glob) >> separator.as(:separator) >> tagvalue_glob.as(:tagvalue_glob) \
113
113
  | tagname_glob.as(:tagname_glob) >> separator.as(:separator) >> tagvalue.as(:tagvalue) \
114
114
  | tagname_glob.as(:tagname_glob) >> separator.as(:separator) \
@@ -117,6 +117,10 @@ module Hotdog
117
117
  | tagname.as(:tagname) >> separator.as(:separator) >> tagvalue.as(:tagvalue) \
118
118
  | tagname.as(:tagname) >> separator.as(:separator) \
119
119
  | tagname.as(:tagname) \
120
+ | (str('@') >> tagname).as(:tagname) >> separator.as(:separator) >> tagvalue_glob.as(:tagvalue_glob) \
121
+ | (str('@') >> tagname).as(:tagname) >> separator.as(:separator) >> tagvalue.as(:tagvalue) \
122
+ | (str('@') >> tagname).as(:tagname) >> separator.as(:separator) \
123
+ | (str('@') >> tagname).as(:tagname) \
120
124
  | separator.as(:separator) >> regexp.as(:tagvalue_regexp) \
121
125
  | separator.as(:separator) >> tagvalue_glob.as(:tagvalue_glob) \
122
126
  | separator.as(:separator) >> tagvalue.as(:tagvalue) \
@@ -1,3 +1,3 @@
1
1
  module Hotdog
2
- VERSION = "0.30.0"
2
+ VERSION = "0.31.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hotdog
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.30.0
4
+ version: 0.31.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Yamashita Yuu
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-11-15 00:00:00.000000000 Z
11
+ date: 2017-11-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler