datadog_backup 2.0.1 → 3.0.0.alpha.2

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.
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module DatadogBackup
4
- VERSION = '2.0.1'
4
+ VERSION = '3.0.0.alpha.2'
5
5
  end
@@ -2,17 +2,18 @@
2
2
 
3
3
  require 'concurrent'
4
4
 
5
- require 'dogapi'
6
-
7
5
  require_relative 'datadog_backup/local_filesystem'
8
6
  require_relative 'datadog_backup/options'
9
-
10
7
  require_relative 'datadog_backup/cli'
11
8
  require_relative 'datadog_backup/core'
12
9
  require_relative 'datadog_backup/dashboards'
13
10
  require_relative 'datadog_backup/monitors'
14
11
  require_relative 'datadog_backup/thread_pool'
15
12
  require_relative 'datadog_backup/version'
13
+ require_relative 'datadog_backup/deprecations'
14
+ DatadogBackup::Deprecations.check
15
+
16
16
 
17
17
  module DatadogBackup
18
18
  end
19
+
@@ -3,64 +3,35 @@
3
3
  require 'spec_helper'
4
4
 
5
5
  describe DatadogBackup::Cli do
6
- let(:api_service_double) { double(Dogapi::APIService) }
7
- let(:client_double) { double }
6
+ let(:stubs) { Faraday::Adapter::Test::Stubs.new }
7
+ let(:api_client_double) { Faraday.new { |f| f.adapter :test, stubs } }
8
8
  let(:tempdir) { Dir.mktmpdir }
9
9
  let(:options) do
10
10
  {
11
11
  action: 'backup',
12
12
  backup_dir: tempdir,
13
- client: client_double,
14
- datadog_api_key: 1,
15
- datadog_app_key: 1,
16
13
  diff_format: nil,
17
- logger: Logger.new('/dev/null'),
18
14
  output_format: :json,
19
15
  resources: [DatadogBackup::Dashboards]
20
16
  }
21
17
  end
22
18
  let(:cli) { described_class.new(options) }
23
- let(:dashboards) { DatadogBackup::Dashboards.new(options) }
19
+ let(:dashboards) do
20
+ dashboards = DatadogBackup::Dashboards.new(options)
21
+ allow(dashboards).to receive(:api_service).and_return(api_client_double)
22
+ return dashboards
23
+ end
24
24
 
25
25
  before do
26
26
  allow(cli).to receive(:resource_instances).and_return([dashboards])
27
27
  end
28
28
 
29
- describe '#initialize_client' do
30
- subject { described_class.new({ datadog_api_key: 1, datadog_app_key: 1 }).initialize_client }
31
-
32
- it { is_expected.to be_a(Dogapi::Client) }
33
-
34
- context 'when the environment variable DATADOG_HOST is set to a custom host like https://api.datadoghq.eu' do
35
- before do
36
- stub_const('ENV', 'DATADOG_HOST' => 'https://api.datadoghq.eu')
37
- end
38
-
39
- describe 'then #datadog_host is https://api.datadoghq.eu' do
40
- subject { described_class.new({ datadog_api_key: 1, datadog_app_key: 1 }).initialize_client.datadog_host }
41
-
42
- it { is_expected.to eq('https://api.datadoghq.eu') }
43
- end
44
- end
45
-
46
- context 'when the environment variable DATADOG_HOST is not set' do
47
- before do
48
- stub_const('ENV', {})
49
- end
50
-
51
- describe 'then #datadog_host is https://api.datadoghq.eu' do
52
- subject { described_class.new({ datadog_api_key: 1, datadog_app_key: 1 }).initialize_client.datadog_host }
53
-
54
- it { is_expected.to eq('https://api.datadoghq.com') }
55
- end
56
- end
57
- end
58
-
59
29
  describe '#backup' do
60
30
  context 'when dashboards are deleted in datadog' do
61
- let(:all_boards) do
31
+ let(:all_dashboards) do
62
32
  [
63
- '200',
33
+ 200,
34
+ {},
64
35
  {
65
36
  'dashboards' => [
66
37
  { 'id' => 'stillthere' },
@@ -75,22 +46,9 @@ describe DatadogBackup::Cli do
75
46
  dashboards.write_file('{"text": "diff"}', "#{tempdir}/dashboards/alsostillthere.json")
76
47
  dashboards.write_file('{"text": "diff"}', "#{tempdir}/dashboards/deleted.json")
77
48
 
78
- allow(client_double).to receive(:instance_variable_get).with(:@dashboard_service).and_return(api_service_double)
79
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get,
80
- '/api/v1/dashboard',
81
- nil,
82
- nil,
83
- false).and_return(all_boards)
84
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get,
85
- '/api/v1/dashboard/stillthere',
86
- nil,
87
- nil,
88
- false).and_return(['200', {}])
89
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get,
90
- '/api/v1/dashboard/alsostillthere',
91
- nil,
92
- nil,
93
- false).and_return(['200', {}])
49
+ stubs.get('/api/v1/dashboard') { all_dashboards }
50
+ stubs.get('/api/v1/dashboard/stillthere') {[200, {}, {}]}
51
+ stubs.get('/api/v1/dashboard/alsostillthere') {[200, {}, {}]}
94
52
  end
95
53
 
96
54
  it 'deletes the file locally as well' do
@@ -108,7 +66,6 @@ describe DatadogBackup::Cli do
108
66
  dashboards.write_file('{"text": "diff"}', "#{tempdir}/dashboards/diffs2.json")
109
67
  dashboards.write_file('{"text": "diff"}', "#{tempdir}/dashboards/diffs3.json")
110
68
  allow(dashboards).to receive(:get_by_id).and_return({ 'text' => 'diff2' })
111
- allow(cli).to receive(:initialize_client).and_return(client_double)
112
69
  end
113
70
 
114
71
  it {
@@ -126,7 +83,6 @@ describe DatadogBackup::Cli do
126
83
  before do
127
84
  dashboards.write_file('{"text": "diff"}', "#{tempdir}/dashboards/diffs1.json")
128
85
  allow(dashboards).to receive(:get_by_id).and_return({ 'text' => 'diff2' })
129
- allow(cli).to receive(:initialize_client).and_return(client_double)
130
86
  end
131
87
 
132
88
  example 'starts interactive restore' do
@@ -3,43 +3,23 @@
3
3
  require 'spec_helper'
4
4
 
5
5
  describe DatadogBackup::Core do
6
- let(:api_service_double) { double(Dogapi::APIService) }
7
- let(:client_double) { double }
6
+ let(:stubs) { Faraday::Adapter::Test::Stubs.new }
7
+ let(:api_client_double) { Faraday.new { |f| f.adapter :test, stubs } }
8
8
  let(:tempdir) { Dir.mktmpdir }
9
9
  let(:core) do
10
- described_class.new(
10
+ core = described_class.new(
11
11
  action: 'backup',
12
- api_service: api_service_double,
13
- client: client_double,
14
12
  backup_dir: tempdir,
15
13
  diff_format: nil,
16
14
  resources: [],
17
- output_format: :json,
18
- logger: Logger.new('/dev/null')
15
+ output_format: :json
19
16
  )
17
+ allow(core).to receive(:api_service).and_return(api_client_double)
18
+ return core
20
19
  end
21
20
 
22
- describe '#client' do
23
- subject { core.client }
24
21
 
25
- it { is_expected.to eq client_double }
26
- end
27
-
28
- describe '#with_200' do
29
- context 'with 200' do
30
- subject { core.with_200 { ['200', { foo: :bar }] } }
31
-
32
- it { is_expected.to eq({ foo: :bar }) }
33
- end
34
22
 
35
- context 'with not 200' do
36
- subject { core.with_200 { ['400', 'Error message'] } }
37
-
38
- it 'raises an error' do
39
- expect { subject }.to raise_error(RuntimeError)
40
- end
41
- end
42
- end
43
23
 
44
24
  describe '#diff' do
45
25
  subject { core.diff('diff') }
@@ -84,52 +64,44 @@ describe DatadogBackup::Core do
84
64
  describe '#create' do
85
65
  subject { core.create({ 'a' => 'b' }) }
86
66
 
87
- example 'it calls Dogapi::APIService.request' do
88
- stub_const('Dogapi::APIService::API_VERSION', 'v1')
89
- allow(core).to receive(:api_service).and_return(api_service_double)
67
+ example 'it will post /api/v1/dashboard' do
90
68
  allow(core).to receive(:api_version).and_return('v1')
91
69
  allow(core).to receive(:api_resource_name).and_return('dashboard')
92
- expect(api_service_double).to receive(:request).with(Net::HTTP::Post,
93
- '/api/v1/dashboard',
94
- nil,
95
- { 'a' => 'b' },
96
- true).and_return(['200', { 'id' => 'whatever-id-abc' }])
70
+ stubs.post('/api/v1/dashboard', {'a' => 'b'}) {[200, {}, {'id' => 'whatever-id-abc' }]}
97
71
  subject
72
+ stubs.verify_stubbed_calls
98
73
  end
99
74
  end
100
75
 
101
76
  describe '#update' do
102
77
  subject { core.update('abc-123-def', { 'a' => 'b' }) }
103
78
 
104
- example 'it calls Dogapi::APIService.request' do
105
- stub_const('Dogapi::APIService::API_VERSION', 'v1')
106
- allow(core).to receive(:api_service).and_return(api_service_double)
79
+ example 'it puts /api/v1/dashboard' do
107
80
  allow(core).to receive(:api_version).and_return('v1')
108
81
  allow(core).to receive(:api_resource_name).and_return('dashboard')
109
- expect(api_service_double).to receive(:request).with(Net::HTTP::Put,
110
- '/api/v1/dashboard/abc-123-def',
111
- nil,
112
- { 'a' => 'b' },
113
- true).and_return(['200', { 'id' => 'whatever-id-abc' }])
82
+ stubs.put('/api/v1/dashboard/abc-123-def', {'a' => 'b'}) {[200, {}, {'id' => 'whatever-id-abc' }]}
114
83
  subject
84
+ stubs.verify_stubbed_calls
85
+ end
86
+
87
+ context 'when the id is not found' do
88
+ before do
89
+ allow(core).to receive(:api_version).and_return('v1')
90
+ allow(core).to receive(:api_resource_name).and_return('dashboard')
91
+ stubs.put('/api/v1/dashboard/abc-123-def', {'a' => 'b'}) {[404, {}, {'id' => 'whatever-id-abc' }]}
92
+ end
93
+ it 'raises an error' do
94
+ expect { subject }.to raise_error(RuntimeError, 'update failed with error 404')
95
+ end
115
96
  end
116
97
  end
117
98
 
118
99
  describe '#restore' do
119
100
  before do
120
- allow(core).to receive(:api_service).and_return(api_service_double)
121
101
  allow(core).to receive(:api_version).and_return('api-version-string')
122
102
  allow(core).to receive(:api_resource_name).and_return('api-resource-name-string')
123
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get,
124
- '/api/api-version-string/api-resource-name-string/abc-123-def',
125
- nil,
126
- nil,
127
- false).and_return(['200', { test: :ok }])
128
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get,
129
- '/api/api-version-string/api-resource-name-string/bad-123-id',
130
- nil,
131
- nil,
132
- false).and_return(['404', { error: :blahblah_not_found }])
103
+ stubs.get('/api/api-version-string/api-resource-name-string/abc-123-def') {[200, {}, {'test' => 'ok' }]}
104
+ stubs.get('/api/api-version-string/api-resource-name-string/bad-123-id') {[404, {}, {'error' => 'blahblah_not_found' }]}
133
105
  allow(core).to receive(:load_from_file_by_id).and_return({ 'load' => 'ok' })
134
106
  end
135
107
 
@@ -142,19 +114,13 @@ describe DatadogBackup::Core do
142
114
  end
143
115
  end
144
116
 
145
- context 'when id does not exist' do
117
+ context 'when id does not exist on remote' do
146
118
  subject { core.restore('bad-123-id') }
147
119
 
148
120
  before do
149
- allow(api_service_double).to receive(:request).with(Net::HTTP::Put,
150
- '/api/api-version-string/api-resource-name-string/bad-123-id',
151
- nil, { 'load' => 'ok' },
152
- true).and_return(['404', { 'Error' => 'my not found' }])
153
- allow(api_service_double).to receive(:request).with(Net::HTTP::Post,
154
- '/api/api-version-string/api-resource-name-string',
155
- nil,
156
- { 'load' => 'ok' },
157
- true).and_return(['200', { 'id' => 'my-new-id' }])
121
+ allow(core).to receive(:load_from_file_by_id).and_return({ 'load' => 'ok' })
122
+ stubs.put('/api/api-version-string/api-resource-name-string/bad-123-id') {[404, {}, {'error' => 'id not found' }]}
123
+ stubs.post('/api/api-version-string/api-resource-name-string', {'load' => 'ok'}) {[200, {}, {'id' => 'my-new-id' }]}
158
124
  end
159
125
 
160
126
  example 'it calls out to create then saves the new file and deletes the new file' do
@@ -3,18 +3,18 @@
3
3
  require 'spec_helper'
4
4
 
5
5
  describe DatadogBackup::Dashboards do
6
- let(:api_service_double) { double(Dogapi::APIService) }
7
- let(:client_double) { double }
6
+ let(:stubs) { Faraday::Adapter::Test::Stubs.new }
7
+ let(:api_client_double) { Faraday.new { |f| f.adapter :test, stubs } }
8
8
  let(:tempdir) { Dir.mktmpdir }
9
9
  let(:dashboards) do
10
- described_class.new(
10
+ dashboards = described_class.new(
11
11
  action: 'backup',
12
- client: client_double,
13
12
  backup_dir: tempdir,
14
13
  output_format: :json,
15
- resources: [],
16
- logger: Logger.new('/dev/null')
14
+ resources: []
17
15
  )
16
+ allow(dashboards).to receive(:api_service).and_return(api_client_double)
17
+ return dashboards
18
18
  end
19
19
  let(:dashboard_description) do
20
20
  {
@@ -23,9 +23,10 @@ describe DatadogBackup::Dashboards do
23
23
  'title' => 'foo'
24
24
  }
25
25
  end
26
- let(:all_boards) do
26
+ let(:all_dashboards) do
27
27
  [
28
- '200',
28
+ 200,
29
+ {},
29
30
  {
30
31
  'dashboards' => [
31
32
  dashboard_description
@@ -35,7 +36,8 @@ describe DatadogBackup::Dashboards do
35
36
  end
36
37
  let(:example_dashboard) do
37
38
  [
38
- '200',
39
+ 200,
40
+ {},
39
41
  board_abc_123_def
40
42
  ]
41
43
  end
@@ -61,11 +63,8 @@ describe DatadogBackup::Dashboards do
61
63
  end
62
64
 
63
65
  before do
64
- allow(client_double).to receive(:instance_variable_get).with(:@dashboard_service).and_return(api_service_double)
65
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get, '/api/v1/dashboard', nil, nil,
66
- false).and_return(all_boards)
67
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get, '/api/v1/dashboard/abc-123-def', nil, nil,
68
- false).and_return(example_dashboard)
66
+ stubs.get('/api/v1/dashboard') { all_dashboards }
67
+ stubs.get('/api/v1/dashboard/abc-123-def') { example_dashboard }
69
68
  end
70
69
 
71
70
  describe '#backup' do
@@ -81,8 +80,8 @@ describe DatadogBackup::Dashboards do
81
80
  end
82
81
  end
83
82
 
84
- describe '#all_boards' do
85
- subject { dashboards.all_boards }
83
+ describe '#all_dashboards' do
84
+ subject { dashboards.all_dashboards }
86
85
 
87
86
  it { is_expected.to eq [dashboard_description] }
88
87
  end
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe DatadogBackup::Deprecations do
6
+ let(:logger) { double }
7
+
8
+ before do
9
+ stub_const('LOGGER', logger)
10
+ allow(logger).to receive(:warn)
11
+ end
12
+
13
+ %w[2.4.10 2.5.9 2.6.8].each do |ruby_version|
14
+ describe "#check#{ruby_version}" do
15
+ subject { described_class.check }
16
+
17
+ it 'does warn' do
18
+ stub_const('RUBY_VERSION', ruby_version)
19
+ expect(logger).to receive(:warn).with(/ruby-#{ruby_version} is deprecated./)
20
+ subject
21
+ end
22
+ end
23
+ end
24
+
25
+ %w[2.7.4 3.0.4 3.1.2 3.2.0-preview1].each do |ruby_version|
26
+ describe "#check#{ruby_version}" do
27
+ subject { described_class.check }
28
+
29
+ it 'does not warn' do
30
+ stub_const('RUBY_VERSION', ruby_version)
31
+ expect(logger).to_not receive(:warn).with(/ruby-#{ruby_version} is deprecated./)
32
+ subject
33
+ end
34
+ end
35
+ end
36
+ end
@@ -3,26 +3,21 @@
3
3
  require 'spec_helper'
4
4
 
5
5
  describe DatadogBackup::LocalFilesystem do
6
- let(:client_double) { double }
7
6
  let(:tempdir) { Dir.mktmpdir }
8
7
  let(:core) do
9
8
  DatadogBackup::Core.new(
10
9
  action: 'backup',
11
- client: client_double,
12
10
  backup_dir: tempdir,
13
11
  resources: [DatadogBackup::Dashboards],
14
- output_format: :json,
15
- logger: Logger.new('/dev/null')
12
+ output_format: :json
16
13
  )
17
14
  end
18
15
  let(:core_yaml) do
19
16
  DatadogBackup::Core.new(
20
17
  action: 'backup',
21
- client: client_double,
22
18
  backup_dir: tempdir,
23
19
  resources: [],
24
- output_format: :yaml,
25
- logger: Logger.new('/dev/null')
20
+ output_format: :yaml
26
21
  )
27
22
  end
28
23
 
@@ -3,19 +3,20 @@
3
3
  require 'spec_helper'
4
4
 
5
5
  describe DatadogBackup::Monitors do
6
- let(:api_service_double) { double(Dogapi::APIService) }
7
- let(:client_double) { double }
6
+ let(:stubs) { Faraday::Adapter::Test::Stubs.new }
7
+ let(:api_client_double) { Faraday.new { |f| f.adapter :test, stubs } }
8
8
  let(:tempdir) { Dir.mktmpdir }
9
9
  let(:monitors) do
10
- described_class.new(
10
+ monitors = described_class.new(
11
11
  action: 'backup',
12
- client: client_double,
13
12
  backup_dir: tempdir,
14
13
  output_format: :json,
15
- resources: [],
16
- logger: Logger.new('/dev/null')
14
+ resources: []
17
15
  )
16
+ allow(monitors).to receive(:api_service).and_return(api_client_double)
17
+ return monitors
18
18
  end
19
+
19
20
  let(:monitor_description) do
20
21
  {
21
22
  'query' => 'bar',
@@ -36,7 +37,8 @@ describe DatadogBackup::Monitors do
36
37
  end
37
38
  let(:all_monitors) do
38
39
  [
39
- '200',
40
+ 200,
41
+ {},
40
42
  [
41
43
  monitor_description
42
44
  ]
@@ -44,17 +46,15 @@ describe DatadogBackup::Monitors do
44
46
  end
45
47
  let(:example_monitor) do
46
48
  [
47
- '200',
49
+ 200,
50
+ {},
48
51
  monitor_description
49
52
  ]
50
53
  end
51
54
 
52
55
  before do
53
- allow(client_double).to receive(:instance_variable_get).with(:@monitor_svc).and_return(api_service_double)
54
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get, '/api/v1/monitor', nil, nil,
55
- false).and_return(all_monitors)
56
- allow(api_service_double).to receive(:request).with(Net::HTTP::Get, '/api/v1/dashboard/123455', nil, nil,
57
- false).and_return(example_monitor)
56
+ stubs.get('/api/v1/monitor') { all_monitors }
57
+ stubs.get('/api/v1/dashboard/123455') { example_monitor }
58
58
  end
59
59
 
60
60
  describe '#all_monitors' do
@@ -79,9 +79,10 @@ describe DatadogBackup::Monitors do
79
79
  describe '#diff and #except' do
80
80
  example 'it ignores `overall_state` and `overall_state_modified`' do
81
81
  monitors.write_file(monitors.dump(monitor_description), monitors.filename(123_455))
82
- allow(api_service_double).to receive(:request).and_return(
82
+ stubs.get('/api/v1/dashboard/123455') {
83
83
  [
84
- '200',
84
+ 200,
85
+ {},
85
86
  [
86
87
  {
87
88
  'query' => 'bar',
@@ -93,7 +94,7 @@ describe DatadogBackup::Monitors do
93
94
  }
94
95
  ]
95
96
  ]
96
- )
97
+ }
97
98
 
98
99
  expect(monitors.diff(123_455)).to eq ''
99
100
 
@@ -17,13 +17,13 @@ describe 'bin/datadog_backup' do
17
17
  i.close
18
18
  end
19
19
 
20
- Timeout.timeout(2.0) do
20
+ Timeout.timeout(4.0) do
21
21
  oe.each do |v|
22
22
  output += v
23
23
  end
24
24
  end
25
25
  rescue Timeout::Error
26
- LOGGER.warn "Timing out #{t.inspect} after 2 second"
26
+ LOGGER.error "Timing out #{t.inspect} after 4 second"
27
27
  Process.kill(15, pid)
28
28
  ensure
29
29
  status = t.value
@@ -32,8 +32,8 @@ describe 'bin/datadog_backup' do
32
32
  end
33
33
 
34
34
  required_vars = %w[
35
- DATADOG_API_KEY
36
- DATADOG_APP_KEY
35
+ DD_API_KEY
36
+ DD_APP_KEY
37
37
  ]
38
38
 
39
39
  env = {}
@@ -52,7 +52,7 @@ describe 'bin/datadog_backup' do
52
52
  it 'supplies help' do
53
53
  stub_const('ENV', env)
54
54
  out_err, status = run_bin('--help')
55
- expect(out_err).to match(/Usage: DATADOG_API_KEY=/)
55
+ expect(out_err).to match(/Usage: DD_API_KEY=/)
56
56
  expect(status).to be_success
57
57
  end
58
58
  end
data/spec/spec_helper.rb CHANGED
@@ -2,16 +2,17 @@
2
2
 
3
3
  $LOAD_PATH.unshift(File.expand_path('../lib', File.dirname(__FILE__)))
4
4
 
5
- require 'datadog_backup'
6
5
  require 'logger'
7
- require 'tmpdir'
8
- require 'dogapi'
9
-
10
6
  $stdout.sync = $stderr.sync = true
11
- LOGGER = Logger.new($stderr) unless defined?(LOGGER)
12
- LOGGER.level = Logger::INFO
7
+ LOGGER = Logger.new($stderr)
8
+ LOGGER.level = Logger::ERROR
13
9
  $stdout = File.new('/dev/null', 'w+')
14
10
 
11
+ require 'tmpdir'
12
+ require 'datadog_backup'
13
+
14
+
15
+
15
16
  SPEC_ROOT = __dir__
16
17
  WORK_ROOT = File.expand_path(File.join(SPEC_ROOT, '..'))
17
18