wavefront-cli 8.5.1 → 9.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (71) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/release.yml +4 -4
  3. data/.github/workflows/test.yml +2 -2
  4. data/.rubocop.yml +1 -4
  5. data/HISTORY.md +12 -0
  6. data/README.md +4 -2
  7. data/lib/wavefront-cli/base.rb +2 -2
  8. data/lib/wavefront-cli/commands/base.rb +10 -9
  9. data/lib/wavefront-cli/commands/derivedmetric.rb +1 -1
  10. data/lib/wavefront-cli/commands/metric.rb +3 -3
  11. data/lib/wavefront-cli/commands/metricspolicy.rb +33 -0
  12. data/lib/wavefront-cli/commands/query.rb +5 -5
  13. data/lib/wavefront-cli/commands/write.rb +12 -12
  14. data/lib/wavefront-cli/config.rb +4 -4
  15. data/lib/wavefront-cli/constants.rb +2 -1
  16. data/lib/wavefront-cli/controller.rb +19 -15
  17. data/lib/wavefront-cli/display/metricspolicy.rb +15 -0
  18. data/lib/wavefront-cli/display/printer/long.rb +11 -13
  19. data/lib/wavefront-cli/display/printer/sparkline.rb +3 -3
  20. data/lib/wavefront-cli/display/query.rb +1 -1
  21. data/lib/wavefront-cli/display/write.rb +2 -1
  22. data/lib/wavefront-cli/event.rb +2 -2
  23. data/lib/wavefront-cli/exception_handler.rb +4 -1
  24. data/lib/wavefront-cli/helpers/load_file.rb +2 -2
  25. data/lib/wavefront-cli/maintenancewindow.rb +1 -1
  26. data/lib/wavefront-cli/metricspolicy.rb +42 -0
  27. data/lib/wavefront-cli/opt_handler.rb +2 -3
  28. data/lib/wavefront-cli/output/csv/query.rb +2 -2
  29. data/lib/wavefront-cli/output/hcl/dashboard.rb +6 -6
  30. data/lib/wavefront-cli/output/hcl/stdlib/array.rb +1 -1
  31. data/lib/wavefront-cli/output/wavefront/query.rb +7 -7
  32. data/lib/wavefront-cli/stdlib/string.rb +4 -4
  33. data/lib/wavefront-cli/usage.rb +1 -1
  34. data/lib/wavefront-cli/version.rb +1 -1
  35. data/lib/wavefront-cli/write.rb +13 -17
  36. data/spec/constants.rb +4 -5
  37. data/spec/support/command_base.rb +12 -0
  38. data/spec/support/minitest_assertions.rb +14 -10
  39. data/spec/support/output_tester.rb +2 -2
  40. data/spec/support/supported_commands.rb +3 -1
  41. data/spec/test_mixins/import.rb +2 -2
  42. data/spec/test_mixins/search.rb +9 -7
  43. data/spec/test_mixins/set.rb +1 -1
  44. data/spec/wavefront-cli/account_spec.rb +6 -4
  45. data/spec/wavefront-cli/alert_spec.rb +29 -6
  46. data/spec/wavefront-cli/commands/base_spec.rb +2 -2
  47. data/spec/wavefront-cli/commands/config_spec.rb +2 -2
  48. data/spec/wavefront-cli/config_spec.rb +3 -3
  49. data/spec/wavefront-cli/controller_spec.rb +2 -0
  50. data/spec/wavefront-cli/dashboard_spec.rb +1 -1
  51. data/spec/wavefront-cli/derivedmetric_spec.rb +9 -7
  52. data/spec/wavefront-cli/display/printer/long_spec.rb +5 -3
  53. data/spec/wavefront-cli/display/printer/terse_spec.rb +1 -1
  54. data/spec/wavefront-cli/event_spec.rb +14 -11
  55. data/spec/wavefront-cli/event_store_spec.rb +16 -12
  56. data/spec/wavefront-cli/externallink_spec.rb +5 -3
  57. data/spec/wavefront-cli/maintenancewindow_spec.rb +25 -19
  58. data/spec/wavefront-cli/message_spec.rb +3 -3
  59. data/spec/wavefront-cli/metricspolicy_spec.rb +30 -0
  60. data/spec/wavefront-cli/opt_handler_spec.rb +1 -1
  61. data/spec/wavefront-cli/output/helpers.rb +1 -1
  62. data/spec/wavefront-cli/proxy_spec.rb +1 -1
  63. data/spec/wavefront-cli/query_spec.rb +1 -1
  64. data/spec/wavefront-cli/role_spec.rb +4 -3
  65. data/spec/wavefront-cli/serviceaccount_spec.rb +7 -5
  66. data/spec/wavefront-cli/stdlib/string_spec.rb +3 -1
  67. data/spec/wavefront-cli/usage_spec.rb +1 -1
  68. data/spec/wavefront-cli/{write_spec.rb → write_class_spec.rb} +1 -14
  69. data/wavefront-cli.gemspec +13 -15
  70. metadata +32 -149
  71. data/spec/spec_helper.rb +0 -113
@@ -27,7 +27,7 @@ module WavefrontCli
27
27
 
28
28
  [%i[CustomerTags atag], %i[HostTags htag],
29
29
  %i[HostNames host]].each do |key, opt|
30
- k = ('relevant' + key.to_s).to_sym
30
+ k = "relevant#{key}".to_sym
31
31
  body[k] = options[opt] unless options[opt].empty?
32
32
  end
33
33
 
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'wavefront-sdk/support/mixins'
4
+ require_relative 'base'
5
+ require_relative 'helpers/load_file'
6
+
7
+ module WavefrontCli
8
+ #
9
+ # CLI coverage for the metricspolicy part of the v2 'usage' API.
10
+ #
11
+ class MetricsPolicy < WavefrontCli::Base
12
+ def do_describe
13
+ wf.describe(options[:version])
14
+ end
15
+
16
+ def do_history
17
+ wf.history(options[:offset] || 0, options[:limit] || 100)
18
+ end
19
+
20
+ def do_revert
21
+ wf.revert(options[:'<version>'])
22
+ end
23
+
24
+ def do_update
25
+ raw = WavefrontCli::Helper::LoadFile.new(options[:'<file>']).load
26
+ rules = process_update(raw)
27
+ wf.update(policyRules: rules)
28
+ end
29
+
30
+ # It looks like the API expects arrays of ID strings for accounts, groups,
31
+ # and roles, but when you export one, those fields are objects with name
32
+ # and ID.
33
+ #
34
+ def process_update(raw)
35
+ raw[:policyRules].tap do |rule|
36
+ rule[:accounts] = rule[:accounts].map { |r| r[:id] }
37
+ rule[:userGroups] = rule[:userGroups].map { |r| r[:id] }
38
+ rule[:roles] = rule[:roles].map { |r| r[:id] }
39
+ end
40
+ end
41
+ end
42
+ end
@@ -43,11 +43,10 @@ module WavefrontCli
43
43
  # constructor.
44
44
  # @param cli_opts [Hash] options from docopt, which may include
45
45
  # the location of the config file and the stanza within it
46
- # @return [Hash] keys are none, one, or both of :file and
47
- # :profile
46
+ # @return [Hash] keys are none, one, or both of :file and :profile
48
47
  #
49
48
  def setup_cred_opts(cli_opts)
50
- cred_opts = { raise_on_no_profile: true }
49
+ cred_opts = cli_opts[:config] ? { raise_on_no_profile: true } : {}
51
50
 
52
51
  if cli_opts[:config]
53
52
  cred_opts[:file] = Pathname.new(cli_opts[:config])
@@ -32,7 +32,7 @@ module WavefrontCsvOutput
32
32
  def raw_output
33
33
  resp.each_with_object([]) do |point, a|
34
34
  point[:points].each do |p|
35
- a.<< csv_format(options[:'<metric>'],
35
+ a << csv_format(options[:'<metric>'],
36
36
  p[:value],
37
37
  p[:timestamp],
38
38
  options[:host],
@@ -48,7 +48,7 @@ module WavefrontCsvOutput
48
48
 
49
49
  resp[:timeseries].each_with_object([]) do |ts, a|
50
50
  ts[:data].each do |point|
51
- a.<< csv_format(ts[:label],
51
+ a << csv_format(ts[:label],
52
52
  point[1],
53
53
  point[0],
54
54
  ts[:host],
@@ -32,19 +32,19 @@ module WavefrontHclOutput
32
32
  # @return [String] HCL list of vals
33
33
  #
34
34
  def listmaker(vals, method)
35
- vals.each_with_object([]) { |v, a| a.<< send(method, v) }.to_hcl_list
35
+ vals.each_with_object([]) { |v, a| a << send(method, v) }.to_hcl_list
36
36
  end
37
37
 
38
38
  def vhandle_sections(vals)
39
39
  vals.each_with_object([]) do |section, a|
40
- a.<< ("name = \"#{section[:name]}\"\n row = " +
40
+ a << ("name = \"#{section[:name]}\"\n row = " +
41
41
  handle_rows(section[:rows])).braced(4)
42
42
  end.to_hcl_list
43
43
  end
44
44
 
45
45
  def handle_rows(rows)
46
46
  rows.each_with_object([]) do |row, a|
47
- a.<< ('chart = ' + handle_charts(row[:charts]).to_s).braced(8)
47
+ a << "chart = #{handle_charts(row[:charts])}".braced(8)
48
48
  end.to_hcl_list
49
49
  end
50
50
 
@@ -58,10 +58,10 @@ module WavefrontHclOutput
58
58
  lines = chart.each_with_object([]) do |(k, v), a|
59
59
  next unless fields.include?(k)
60
60
 
61
- a.<< format('%<key>s = %<value>s', key: k, value: quote_value(v))
61
+ a << format('%<key>s = %<value>s', key: k, value: quote_value(v))
62
62
  end
63
63
 
64
- lines.<< "source = #{handle_sources(chart[:sources])}"
64
+ lines << "source = #{handle_sources(chart[:sources])}"
65
65
  lines.to_hcl_obj(10)
66
66
  end
67
67
 
@@ -75,7 +75,7 @@ module WavefrontHclOutput
75
75
 
76
76
  k = 'queryBuilderEnabled' if k == 'querybuilderEnabled'
77
77
 
78
- a.<< format('%<key>s = %<value>s',
78
+ a << format('%<key>s = %<value>s',
79
79
  key: k.to_snake,
80
80
  value: quote_value(v))
81
81
  end.to_hcl_obj(14)
@@ -9,7 +9,7 @@ class Array
9
9
  # @return [String]
10
10
  #
11
11
  def to_hcl_list
12
- '[' + join(',') + ']'
12
+ "[#{join(',')}]"
13
13
  end
14
14
 
15
15
  # Turn an array into a string which represents an HCL object
@@ -20,11 +20,11 @@ module WavefrontWavefrontOutput
20
20
  def raw_output
21
21
  resp.each_with_object('') do |point, a|
22
22
  point[:points].each do |p|
23
- a.<< wavefront_format(options[:'<metric>'],
24
- p[:value],
25
- p[:timestamp],
26
- options[:host],
27
- point[:tags]) + "\n"
23
+ a << "#{wavefront_format(options[:'<metric>'],
24
+ p[:value],
25
+ p[:timestamp],
26
+ options[:host],
27
+ point[:tags])}\n"
28
28
  end
29
29
  end
30
30
  end
@@ -34,7 +34,7 @@ module WavefrontWavefrontOutput
34
34
 
35
35
  resp[:timeseries].each_with_object([]) do |ts, a|
36
36
  ts[:data].each do |point|
37
- a.<< wavefront_format(ts[:label],
37
+ a << wavefront_format(ts[:label],
38
38
  point[1],
39
39
  point[0],
40
40
  ts[:host],
@@ -46,7 +46,7 @@ module WavefrontWavefrontOutput
46
46
  def wavefront_format(path, value, timestamp, source, tags = nil)
47
47
  arr = [path, value, timestamp, format('source=%<source>s',
48
48
  source: source)]
49
- arr.<< tags.to_wf_tag if tags && !tags.empty?
49
+ arr << tags.to_wf_tag if tags && !tags.empty?
50
50
  arr.join(' ')
51
51
  end
52
52
  end
@@ -10,7 +10,7 @@ class String
10
10
  # @param indent [Integer] size of hanging indent, in chars
11
11
  #
12
12
  def cmd_fold(twidth = TW, indent = 10)
13
- gsub(/(-\w) /, '\\1^').scan_line(twidth - 12).join("\n" + ' ' * indent)
13
+ gsub(/(-\w) /, '\\1^').scan_line(twidth - 12).join("\n#{' ' * indent}")
14
14
  .restored
15
15
  end
16
16
 
@@ -58,7 +58,7 @@ class String
58
58
  #
59
59
  def value_fold(indent = 0, twidth = TW)
60
60
  max_line_length = twidth - indent - 4
61
- scan_line(max_line_length).join("\n" + ' ' * indent)
61
+ scan_line(max_line_length).join("\n#{' ' * indent}")
62
62
  end
63
63
 
64
64
  # @param width [Integer] length of longest string (width of
@@ -94,7 +94,7 @@ class String
94
94
  #
95
95
  def to_snake
96
96
  gsub(/(.)([A-Z])/) do
97
- Regexp.last_match[1] + '_' + Regexp.last_match[2].downcase
97
+ "#{Regexp.last_match[1]}_#{Regexp.last_match[2].downcase}"
98
98
  end
99
99
  end
100
100
 
@@ -102,7 +102,7 @@ class String
102
102
 
103
103
  def indent_folded_lines(chunks, twidth, indent, prefix)
104
104
  chunks.join(' ').scan_line(twidth - indent - 5).map do |line|
105
- prefix + ' ' * indent + line
105
+ "#{prefix}#{' ' * indent}#{line}"
106
106
  end
107
107
  end
108
108
  end
@@ -18,7 +18,7 @@ module WavefrontCli
18
18
  end
19
19
 
20
20
  def default_start
21
- parse_time(Time.now - 60 * 60 * 24)
21
+ parse_time(Time.now - 86_400)
22
22
  end
23
23
  end
24
24
  end
@@ -1,3 +1,3 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- WF_CLI_VERSION = '8.5.1'
3
+ WF_CLI_VERSION = '9.0.0'
@@ -74,8 +74,8 @@ module WavefrontCli
74
74
  end
75
75
  # rubocop:enable Metrics/AbcSize
76
76
 
77
- # Turn our user's representation of a distribution into one
78
- # which suits Wavefront. The SDK can do this for us.
77
+ # Turn our user's representation of a distribution into one which suits
78
+ # Wavefront. The SDK can do this for us.
79
79
  #
80
80
  def mk_dist
81
81
  xpanded = expand_dist(options[:'<val>'])
@@ -83,7 +83,11 @@ module WavefrontCli
83
83
  end
84
84
 
85
85
  def extra_options
86
- options[:using] ? { writer: options[:using] } : {}
86
+ if options[:using]
87
+ { writer: options[:using] }
88
+ else
89
+ { writer: :http }
90
+ end
87
91
  end
88
92
 
89
93
  # I chose to prioritise UI consistency over internal elegance
@@ -108,6 +112,7 @@ module WavefrontCli
108
112
  port: options[:port] || default_port,
109
113
  socket: options[:socket],
110
114
  endpoint: options[:endpoint],
115
+ agent: "wavefront-cli-#{WF_CLI_VERSION}",
111
116
  token: options[:token] }
112
117
  end
113
118
 
@@ -115,18 +120,9 @@ module WavefrontCli
115
120
  distribution? ? 40_000 : 2878
116
121
  end
117
122
 
123
+ # The SDK writer plugins validate the credentials they need
118
124
  def validate_opts
119
125
  validate_opts_file if options[:file]
120
-
121
- if options[:using] == 'unix'
122
- return true if options[:socket]
123
-
124
- raise(WavefrontCli::Exception::CredentialError, 'No socket path.')
125
- end
126
-
127
- return true if options[:proxy]
128
-
129
- raise(WavefrontCli::Exception::CredentialError, 'No proxy address.')
130
126
  end
131
127
 
132
128
  def validate_opts_file
@@ -167,7 +163,7 @@ module WavefrontCli
167
163
  #
168
164
  def process_input_file(data)
169
165
  data.each_with_object([]) do |l, a|
170
- a.<< process_line(l)
166
+ a << process_line(l)
171
167
  rescue WavefrontCli::Exception::UnparseableInput => e
172
168
  puts "Bad input. #{e.message}."
173
169
  next
@@ -426,17 +422,17 @@ module WavefrontCli
426
422
  #
427
423
  def valid_timestamp?(timestamp)
428
424
  (timestamp.is_a?(Integer) ||
429
- timestamp.is_a?(String) && timestamp.match(/^\d+$/)) &&
425
+ (timestamp.is_a?(String) && timestamp.match(/^\d+$/))) &&
430
426
  timestamp.to_i > 946_684_800 &&
431
427
  timestamp.to_i < (Time.now.to_i + 31_557_600)
432
428
  end
433
429
 
434
430
  def setup_fmt(fmt)
435
- @fmt = fmt.split('')
431
+ @fmt = fmt.chars
436
432
  end
437
433
 
438
434
  def load_data(file)
439
- IO.read(file)
435
+ File.read(file)
440
436
  rescue StandardError
441
437
  raise WavefrontCli::Exception::FileNotFound
442
438
  end
data/spec/constants.rb CHANGED
@@ -12,10 +12,9 @@ TW = 80
12
12
 
13
13
  ENDPOINT = 'metrics.wavefront.com'
14
14
  TOKEN = '0123456789-ABCDEF'
15
- RES_DIR = ROOT + 'spec' + 'wavefront-cli' + 'resources'
16
- CF = RES_DIR + 'wavefront.conf'
15
+ RES_DIR = ROOT.join('spec', 'wavefront-cli', 'resources')
16
+ CF = RES_DIR.join('wavefront.conf')
17
17
  CF_VAL = IniFile.load(CF)
18
- JSON_POST_HEADERS = {
19
- 'Content-Type': 'application/json', Accept: 'application/json'
20
- }.freeze
18
+ JSON_POST_HEADERS = { 'Content-Type': 'application/json',
19
+ Accept: 'application/json' }.freeze
21
20
  TEE_ZERO = Time.now.freeze
@@ -9,11 +9,13 @@ require_relative '../../lib/wavefront-cli/controller'
9
9
  # commands.
10
10
  #
11
11
  class EndToEndTest < MiniTest::Test
12
+ attr_accessor :single_perm
12
13
  attr_reader :wf
13
14
 
14
15
  def setup
15
16
  before_setup if respond_to?(:before_setup)
16
17
  @wf = WavefrontCliController
18
+ @single_perm = false
17
19
  end
18
20
 
19
21
  def api_path
@@ -79,4 +81,14 @@ class EndToEndTest < MiniTest::Test
79
81
  { status: { result: 'OK', message: '', code: 200 },
80
82
  items: [] }.to_json
81
83
  end
84
+
85
+ def blank_envvars
86
+ %w[WAVEFRONT_ENDPOINT WAVEFRONT_PROXY WAVEFRONT_TOKEN].each do |v|
87
+ ENV[v] = nil
88
+ end
89
+ end
90
+
91
+ def config?
92
+ Pathname.new(Dir.home).join('.wavefront').exist?
93
+ end
82
94
  end
@@ -147,10 +147,13 @@ module Minitest
147
147
  end
148
148
 
149
149
  def assert_cmd_posts(command, api_path, payload = 'null',
150
- response = dummy_response)
150
+ response = nil, extra_headers = {})
151
+ response ||= dummy_response
151
152
  all_permutations do |p|
152
153
  assert_posts("https://#{p[:endpoint]}#{api_path}",
153
- mk_headers(p[:token]), payload, response) do
154
+ mk_headers(p[:token], extra_headers),
155
+ payload,
156
+ response) do
154
157
  wf.new("#{cmd_word} #{command} #{p[:cmdline]}".split)
155
158
  end
156
159
  end
@@ -166,7 +169,7 @@ module Minitest
166
169
  end
167
170
 
168
171
  def assert_cmd_deletes(command, api_path, response = dummy_response)
169
- permutations.each do |p|
172
+ all_permutations do |p|
170
173
  assert_deletes("https://#{p[:endpoint]}#{api_path}",
171
174
  mk_headers(p[:token]), response) do
172
175
  wf.new("#{cmd_word} #{command} #{p[:cmdline]}".split)
@@ -188,13 +191,14 @@ module Minitest
188
191
  assert_empty(err)
189
192
  end
190
193
 
191
- # Run tests with all available permutations. We'll always need
192
- # to mock out display, unless we don't, when even if we do, it
193
- # won't matter.
194
+ # Run tests with all available permutations, unless the single_perm class
195
+ # variable is set. This lets us run tests faster by running fewer (but
196
+ # still a good random selection) and lets us run tests which must only be
197
+ # run once, like tests which pop stuff off the event stack.
194
198
  #
195
199
  def all_permutations
196
200
  perms = permutations
197
- perms = [perms[2]]
201
+ perms = perms.shuffle.take(1) if @single_perm || ENV['FAST_TESTS']
198
202
 
199
203
  perms.each do |p|
200
204
  yield(p)
@@ -213,11 +217,11 @@ module Minitest
213
217
 
214
218
  private
215
219
 
216
- def mk_headers(token = nil)
220
+ def mk_headers(token = nil, extra_headers = {})
217
221
  { Accept: /.*/,
218
222
  'Accept-Encoding': /.*/,
219
- Authorization: 'Bearer ' + (token || '0123456789-ABCDEF'),
220
- 'User-Agent': "wavefront-cli-#{WF_CLI_VERSION}" }
223
+ Authorization: "Bearer #{token || '0123456789-ABCDEF'}",
224
+ 'User-Agent': "wavefront-cli-#{WF_CLI_VERSION}" }.merge(extra_headers)
221
225
  end
222
226
 
223
227
  # Every command we simulate running is done under the following
@@ -14,7 +14,7 @@ class OutputTester
14
14
  # @return [Object] canned raw responses used to test outputs
15
15
  #
16
16
  def load_input(file, only_items = true)
17
- ret = JSON.parse(IO.read(RES_DIR + 'display' + file),
17
+ ret = JSON.parse(File.read(RES_DIR.join('display', file)),
18
18
  symbolize_names: true)
19
19
  only_items ? ret[:items] : ret
20
20
  end
@@ -23,7 +23,7 @@ class OutputTester
23
23
  # @return [String]
24
24
  #
25
25
  def load_expected(file)
26
- IO.read(RES_DIR + 'display' + file)
26
+ File.read(RES_DIR.join('display', file))
27
27
  end
28
28
 
29
29
  def in_and_out(input, expected, only_items = true)
@@ -2,11 +2,13 @@
2
2
 
3
3
  require_relative '../constants'
4
4
 
5
+ # Produces a list of wf's commands
6
+ #
5
7
  class SupportedCommands
6
8
  attr_reader :cmd_dir
7
9
 
8
10
  def initialize
9
- @cmd_dir = ROOT + 'lib' + 'wavefront-cli' + 'commands'
11
+ @cmd_dir = ROOT.join('lib', 'wavefront-cli', 'commands')
10
12
  end
11
13
 
12
14
  def all
@@ -61,11 +61,11 @@ module WavefrontCliTest
61
61
  private
62
62
 
63
63
  def import_file
64
- RES_DIR + 'imports' + "#{api_path}.json"
64
+ RES_DIR.join('imports', "#{api_path}.json")
65
65
  end
66
66
 
67
67
  def update_file
68
- RES_DIR + 'updates' + "#{api_path}.json"
68
+ RES_DIR.join('updates', "#{api_path}.json")
69
69
  end
70
70
  end
71
71
  end
@@ -18,17 +18,19 @@ module WavefrontCliTest
18
18
  sort: { field: 'id', ascending: true })
19
19
  end
20
20
 
21
+ json_body = { limit: 10,
22
+ offset: 0,
23
+ query: [{ key: 'id',
24
+ value: id,
25
+ matchingMethod: 'EXACT',
26
+ negated: false }],
27
+ sort: { field: 'id', ascending: true } }.to_json
28
+
21
29
  assert_noop(
22
30
  "search id=#{id}",
23
31
  'uri: POST https://default.wavefront.com/api/v2/search/' \
24
32
  "#{search_api_path}",
25
- 'body: ' + { limit: 10,
26
- offset: 0,
27
- query: [{ key: 'id',
28
- value: id,
29
- matchingMethod: 'EXACT',
30
- negated: false }],
31
- sort: { field: 'id', ascending: true } }.to_json
33
+ "body: #{json_body}"
32
34
  )
33
35
  assert_abort_on_missing_creds("search id=#{id}")
34
36
  assert_usage('search')
@@ -23,7 +23,7 @@ module WavefrontCliTest
23
23
 
24
24
  def run_command(perm)
25
25
  wf.new("#{cmd_word} set #{set_key}=new_value #{id} " \
26
- "#{perm[:cmdline]}".split)
26
+ "#{perm[:cmdline]}".split)
27
27
  rescue SystemExit => e
28
28
  p e
29
29
  end
@@ -228,10 +228,12 @@ class AccountEndToEndTest < EndToEndTest
228
228
  cmd = "validate #{user_list.join(' ')}"
229
229
 
230
230
  quietly do
231
- assert_cmd_posts(cmd,
232
- '/api/v2/account/validateAccounts',
233
- user_list.to_json,
234
- IO.read(RES_DIR + 'responses' + 'user-validate.json'))
231
+ assert_cmd_posts(
232
+ cmd,
233
+ '/api/v2/account/validateAccounts',
234
+ user_list.to_json,
235
+ File.read(RES_DIR.join('responses', 'user-validate.json'))
236
+ )
235
237
  end
236
238
 
237
239
  assert_noop(cmd,
@@ -21,6 +21,25 @@ class AlertEndToEndTest < EndToEndTest
21
21
  include WavefrontCliTest::History
22
22
  include WavefrontCliTest::Acl
23
23
 
24
+ # This test isn't run if whoever runs it has a config file, because it tests
25
+ # wf's behaviour only if that file does not exist. CI will never have that
26
+ # file.
27
+ #
28
+ def test_no_config_no_envvars
29
+ skip if config?
30
+
31
+ blank_envvars
32
+ wf = WavefrontCliController
33
+
34
+ out, err = capture_io do
35
+ assert_raises(SystemExit) { wf.new(%w[alert list]) }
36
+ end
37
+
38
+ assert_empty(err)
39
+ assert out.start_with?('Credential error. Missing api token.')
40
+ assert_match(/You may also run 'wf config setup'/, out)
41
+ end
42
+
24
43
  def test_latest
25
44
  quietly do
26
45
  assert_cmd_gets("latest #{id}", "/api/v2/alert/#{id}/history")
@@ -48,10 +67,12 @@ class AlertEndToEndTest < EndToEndTest
48
67
  id: id, v: nil, name: nil)
49
68
  end
50
69
 
70
+ json_body = { id: id, name: nil, v: nil }.to_json
71
+
51
72
  assert_noop("clone #{id}",
52
73
  'uri: POST https://default.wavefront.com/api/v2/' \
53
74
  "alert/#{id}/clone",
54
- 'body: ' + { id: id, name: nil, v: nil }.to_json)
75
+ "body: #{json_body}")
55
76
 
56
77
  assert_invalid_id("clone #{invalid_id}")
57
78
  assert_usage('clone')
@@ -65,10 +86,12 @@ class AlertEndToEndTest < EndToEndTest
65
86
  id: id, v: 5, name: nil)
66
87
  end
67
88
 
89
+ json_body = { id: id, name: nil, v: 5 }.to_json
90
+
68
91
  assert_noop("clone #{id} --version 5",
69
92
  'uri: POST https://default.wavefront.com/api/v2/' \
70
93
  "alert/#{id}/clone",
71
- 'body: ' + { id: id, name: nil, v: 5 }.to_json)
94
+ "body: #{json_body}")
72
95
 
73
96
  assert_invalid_id("clone -v 10 #{invalid_id}")
74
97
  assert_usage('clone -v')
@@ -173,7 +196,7 @@ class AlertEndToEndTest < EndToEndTest
173
196
  assert_noop('snoozed',
174
197
  'uri: POST https://default.wavefront.com/api/v2/' \
175
198
  'search/alert',
176
- 'body: ' + state_search('snoozed').to_json)
199
+ "body: #{state_search('snoozed').to_json}")
177
200
 
178
201
  assert_abort_on_missing_creds('snoozed')
179
202
  end
@@ -193,7 +216,7 @@ class AlertEndToEndTest < EndToEndTest
193
216
  assert_noop('firing',
194
217
  'uri: POST https://default.wavefront.com/api/v2/' \
195
218
  'search/alert',
196
- 'body: ' + state_search('firing').to_json)
219
+ "body: #{state_search('firing').to_json}")
197
220
 
198
221
  assert_abort_on_missing_creds('firing')
199
222
  end
@@ -213,7 +236,7 @@ class AlertEndToEndTest < EndToEndTest
213
236
  assert_noop('currently firing',
214
237
  'uri: POST https://default.wavefront.com/api/v2/' \
215
238
  'search/alert',
216
- 'body: ' + state_search('firing').to_json)
239
+ "body: #{state_search('firing').to_json}")
217
240
 
218
241
  assert_abort_on_missing_creds('currently firing')
219
242
  end
@@ -233,7 +256,7 @@ class AlertEndToEndTest < EndToEndTest
233
256
  assert_noop('currently in_maintenance',
234
257
  'uri: POST https://default.wavefront.com/api/v2/' \
235
258
  'search/alert',
236
- 'body: ' + state_search('in_maintenance').to_json)
259
+ "body: #{state_search('in_maintenance').to_json}")
237
260
 
238
261
  assert_abort_on_missing_creds('currently in_maintenance')
239
262
  end
@@ -68,7 +68,7 @@ class WavefrontCommmandBaseTest < MiniTest::Test
68
68
  assert wf.commands.start_with?("Usage:\n")
69
69
  assert wf.commands.match(/ --help$/)
70
70
 
71
- wf.commands(600).split("\n")[1..-1].each do |c|
71
+ wf.commands(600).split("\n")[1..].each do |c|
72
72
  next if skip_cmd && c.match(skip_cmd)
73
73
 
74
74
  assert_match(/^ \w+/, c)
@@ -80,7 +80,7 @@ class WavefrontCommmandBaseTest < MiniTest::Test
80
80
  assert wf.options(600).start_with?("Global options:\n")
81
81
  assert_match(/\nOptions:/, wf.options)
82
82
 
83
- wf.options(600).split("\n")[1..-1].each do |o|
83
+ wf.options(600).split("\n")[1..].each do |o|
84
84
  next if o == 'Global options:' || o == 'Options:' || o.empty?
85
85
 
86
86
  assert_instance_of(String, o)
@@ -20,7 +20,7 @@ class WavefrontCommmandConfigTest < WavefrontCommmandBaseTest
20
20
  refute wf.options(600).start_with?("Global options:\n")
21
21
  assert_match(/Options:\n/, wf.options)
22
22
 
23
- wf.options(600).split("\n")[1..-1].each do |o|
23
+ wf.options(600).split("\n")[1..].each do |o|
24
24
  next if o == 'Global options:' || o == 'Options:' || o.empty?
25
25
 
26
26
  assert_instance_of(String, o)
@@ -35,7 +35,7 @@ class WavefrontCommmandConfigTest < WavefrontCommmandBaseTest
35
35
  assert wf.commands.start_with?("Usage:\n")
36
36
  assert wf.commands.match(/ --help$/)
37
37
 
38
- wf.commands(600).split("\n")[1..-1].each do |c|
38
+ wf.commands(600).split("\n")[1..].each do |c|
39
39
  next if skip_cmd && c.match(skip_cmd)
40
40
 
41
41
  assert_match(/^ \w+/, c)