awspec 1.24.3 → 1.24.4

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
  SHA256:
3
- metadata.gz: 9ac14ec851ce396f40316106c3784538793a8522009cc6d2172b71d01bc16691
4
- data.tar.gz: 291660659e3c9223777f70e779c1d2ab34a591a4bfd83590002764977a70e73d
3
+ metadata.gz: 03a271717bc3471b5109a4831bbb0941a1d2975b90ed04427fa304fb727c251b
4
+ data.tar.gz: 3eff98cd7e63f51067739eebf9d8c94476b66469ea98b2148d96c9afec502c3d
5
5
  SHA512:
6
- metadata.gz: 411f890f896ba013a75805159318bca637f0c43f0cc2b62c9e745d3b3386a31ba24d2080c1f4821f6fd68d5392bd1003a03838f119fa156b28f1959d4016ef98
7
- data.tar.gz: f9ee6a4015f25bb56b85ae3a741a628bc5985b4e85f04e92099faaa9fb14caf02d7e8a13ef6ec86e3e5cd51455fe0b1d7d6fcc6feed3853d88661233f4079afd
6
+ metadata.gz: 82d89949fa055cbcfda478ff3efa28259a70cf9dc37fba9ea2c9e861c6393e225c5d268b701acdd4c567b0878d4d06f3c2db692b554d41a9737cecac87cc6dab
7
+ data.tar.gz: 9d5a864c8065cf512aabcb2c2dd8851510253d8486dc0d6653e5c53d4c50376ca9c53a4a7ad45db5c8841e38d6c210a6e14c90970fabb75e03a454f4730cdaf3
@@ -0,0 +1,69 @@
1
+ name: CI
2
+
3
+ on:
4
+ push:
5
+ branches: [ master ]
6
+ pull_request:
7
+
8
+ jobs:
9
+ lint:
10
+ name: Lint
11
+ runs-on: ubuntu-latest
12
+
13
+ steps:
14
+ - name: Checkout
15
+ uses: actions/checkout@v2
16
+
17
+ - name: Set up Ruby
18
+ uses: ruby/setup-ruby@v1
19
+ with:
20
+ ruby-version: 2.7
21
+ bundler-cache: true
22
+
23
+ - name: Run rubocop
24
+ uses: reviewdog/action-rubocop@v1
25
+ with:
26
+ rubocop_version: 0.57.2
27
+ rubocop_extensions: rubocop:0.57.2
28
+ github_token: ${{ secrets.GITHUB_TOKEN }}
29
+ reporter: github-pr-review
30
+ fail_on_error: true
31
+
32
+ test:
33
+ name: Test
34
+ needs: [ lint ]
35
+ strategy:
36
+ fail-fast: false
37
+ matrix:
38
+ ruby-version:
39
+ - '2.1'
40
+ - '2.2'
41
+ - '2.3'
42
+ - '2.4'
43
+ - '2.5'
44
+ - '2.6'
45
+ - '2.7'
46
+ # - '3.0'
47
+ runs-on: ubuntu-latest
48
+ env:
49
+ DISABLE_AWS_CLIENT_CHECK: true
50
+
51
+ steps:
52
+ - name: Checkout
53
+ uses: actions/checkout@v2
54
+
55
+ - name: Set up Ruby
56
+ uses: ruby/setup-ruby@v1
57
+ with:
58
+ ruby-version: ${{ matrix.ruby-version }}
59
+ bundler-cache: true
60
+
61
+ - name: Install xml lib
62
+ run: gem install ox
63
+ if: matrix.ruby-version == '3.0'
64
+
65
+ - name: Generate document
66
+ run: bundle exec bin/toolbox docgen > doc/resource_types.md
67
+
68
+ - name: Run tests
69
+ run: bundle exec rake spec
@@ -0,0 +1,29 @@
1
+ name: Doc
2
+
3
+ on:
4
+ schedule:
5
+ - cron: '0 0 * * 0'
6
+
7
+ jobs:
8
+ doc:
9
+ name: Document
10
+ runs-on: ubuntu-latest
11
+ env:
12
+ DISABLE_AWS_CLIENT_CHECK: true
13
+ steps:
14
+ - name: Checkout
15
+ uses: actions/checkout@v2
16
+
17
+ - name: Set up Ruby
18
+ uses: ruby/setup-ruby@v1
19
+ with:
20
+ ruby-version: '2.7'
21
+ bundler-cache: true
22
+
23
+ - name: Generate document
24
+ run: bundle exec bin/toolbox docgen > doc/resource_types.md
25
+
26
+ - uses: EndBug/add-and-commit@v7
27
+ with:
28
+ default_author: github_actions
29
+ add: 'doc/resource_types.md'
data/.rubocop.yml CHANGED
@@ -10,12 +10,24 @@ Layout/MultilineOperationIndentation:
10
10
  Layout/MultilineMethodCallBraceLayout:
11
11
  Enabled: false
12
12
 
13
+ Layout/ClosingHeredocIndentation:
14
+ Enabled: false
15
+
16
+ Layout/SpaceInsideArrayLiteralBrackets:
17
+ Enabled: false
18
+
13
19
  Lint/HandleExceptions:
14
20
  Enabled: false
15
21
 
16
22
  Lint/UselessAssignment:
17
23
  Enabled: false
18
24
 
25
+ Lint/DuplicateMethods:
26
+ Enabled: false
27
+
28
+ Lint/MissingCopEnableDirective:
29
+ Enabled: false
30
+
19
31
  Metrics/AbcSize:
20
32
  Max: 50
21
33
 
@@ -41,7 +53,13 @@ Metrics/ModuleLength:
41
53
  Metrics/PerceivedComplexity:
42
54
  Max: 15
43
55
 
44
- Style/PredicateName:
56
+ Naming/UncommunicativeMethodParamName:
57
+ Enabled: false
58
+
59
+ Naming/PredicateName:
60
+ Enabled: false
61
+
62
+ Naming/HeredocDelimiterNaming:
45
63
  Enabled: false
46
64
 
47
65
  Performance/StringReplacement:
@@ -65,7 +83,10 @@ Style/ClassAndModuleChildren:
65
83
  Style/Documentation:
66
84
  Enabled: false
67
85
 
68
- Style/MethodMissing:
86
+ Style/MethodMissingSuper:
87
+ Enabled: false
88
+
89
+ Style/MissingRespondToMissing:
69
90
  Enabled: false
70
91
 
71
92
  Style/MutableConstant:
@@ -91,3 +112,27 @@ Style/SymbolProc:
91
112
 
92
113
  Style/YodaCondition:
93
114
  Enabled: false
115
+
116
+ Style/RescueStandardError:
117
+ Enabled: false
118
+
119
+ Style/RedundantReturn:
120
+ Enabled: false
121
+
122
+ Style/ConditionalAssignment:
123
+ Enabled: false
124
+
125
+ Style/EvalWithLocation:
126
+ Enabled: false
127
+
128
+ Style/MixinUsage:
129
+ Exclude:
130
+ - 'lib/awspec/helper.rb'
131
+
132
+ Style/StderrPuts:
133
+ Exclude:
134
+ - 'lib/awspec/generator/template.rb'
135
+ - 'lib/awspec/setup.rb'
136
+
137
+ Style/IfUnlessModifier:
138
+ Enabled: false
data/Gemfile CHANGED
@@ -2,3 +2,5 @@ source 'https://rubygems.org'
2
2
 
3
3
  # Specify your gem's dependencies in awspec.gemspec
4
4
  gemspec
5
+
6
+ # gem 'ox' if Gem::Version.create(RUBY_VERSION) >= Gem::Version.create('3.0.0')
data/README.md CHANGED
@@ -1,11 +1,9 @@
1
- # awspec [![Gem](https://img.shields.io/gem/v/awspec.svg)](https://rubygems.org/gems/awspec) [![Travis](https://img.shields.io/travis/k1LoW/awspec.svg)](https://travis-ci.org/k1LoW/awspec)
1
+ # awspec [![Gem](https://img.shields.io/gem/v/awspec.svg)](https://rubygems.org/gems/awspec) [![CI](https://github.com/k1LoW/awspec/actions/workflows/ci.yml/badge.svg)](https://github.com/k1LoW/awspec/actions)
2
2
 
3
3
  ![Logo](./awspec-logo.png)
4
4
 
5
5
  RSpec tests for your AWS resources.
6
6
 
7
- [![Join the chat at https://gitter.im/k1LoW/awspec](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/k1LoW/awspec?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
8
-
9
7
  [Resource Types](doc/resource_types.md) | [Contributing](doc/contributing.md)
10
8
 
11
9
  ## Installation
data/Rakefile CHANGED
@@ -23,7 +23,6 @@ if defined?(RSpec)
23
23
  'spec:core',
24
24
  'spec:generator_spec',
25
25
  'spec:generator_doc',
26
- 'spec:rubocop',
27
26
  'spec:helper']
28
27
 
29
28
  task type: types
data/awspec.gemspec CHANGED
@@ -1,6 +1,4 @@
1
- # coding: utf-8
2
-
3
- lib = File.expand_path('../lib', __FILE__)
1
+ lib = File.expand_path('lib', __dir__)
4
2
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
3
  require 'awspec/version'
6
4
 
@@ -21,6 +19,7 @@ Gem::Specification.new do |spec|
21
19
  spec.require_paths = ['lib']
22
20
 
23
21
  spec.required_ruby_version = '>= 2.1'
22
+ spec.add_runtime_dependency 'addressable'
24
23
  spec.add_runtime_dependency 'aws-sdk', '~> 3'
25
24
  spec.add_runtime_dependency 'awsecrets', '~> 1'
26
25
  spec.add_runtime_dependency 'dry-inflector'
@@ -29,10 +28,9 @@ Gem::Specification.new do |spec|
29
28
  spec.add_runtime_dependency 'rspec-its'
30
29
  spec.add_runtime_dependency 'term-ansicolor'
31
30
  spec.add_runtime_dependency 'thor'
32
- spec.add_runtime_dependency 'addressable'
33
31
  spec.add_development_dependency 'bundler', '>= 1.9', '< 3.0'
34
32
  spec.add_development_dependency 'octorelease'
35
33
  spec.add_development_dependency 'pry'
36
34
  spec.add_development_dependency 'rake', '~> 12.0'
37
- spec.add_development_dependency 'rubocop', '~> 0.49.0'
35
+ spec.add_development_dependency 'rubocop', '~> 0.57.0'
38
36
  end
@@ -21,6 +21,15 @@ describe cloudwatch_logs('my-cloudwatch-logs-group') do
21
21
  it { should have_metric_filter('my-cloudwatch-logs-metric-filter') }
22
22
  end
23
23
  ```
24
+ or
25
+ ```ruby
26
+ describe cloudwatch_logs('my-cloudwatch-logs-group') do
27
+ it do
28
+ should have_metric_filter('my-cloudwatch-logs-metric-filter')
29
+ .filter_pattern('[date, error]')
30
+ end
31
+ end
32
+ ```
24
33
 
25
34
  ### have_subscription_filter
26
35
 
@@ -5,6 +5,25 @@ describe eks_nodegroup('my-eks-nodegroup'), cluster: 'my-cluster' do
5
5
  it { should exist }
6
6
  end
7
7
  ```
8
+
9
+ ### have_security_group
10
+
11
+ ```ruby
12
+ describe eks_nodegroup('my-eks-nodegroup'), cluster: 'my-cluster' do
13
+ it { should have_security_group('sg-1a2b3cd4') }
14
+ end
15
+ ```
16
+
17
+ ### scaling_config
18
+
19
+ ```ruby
20
+ describe eks_nodegroup('my-eks-nodegroup'), cluster: 'my-cluster' do
21
+ its('scaling_config.min_size') { should eq 1 }
22
+ its('scaling_config.desired_size') { should eq 2 }
23
+ its('scaling_config.max_size') { should eq 3 }
24
+ end
25
+ ```
26
+
8
27
  ### be_active, be_creating
9
28
 
10
29
  ```ruby
@@ -12,3 +31,37 @@ describe eks('my-eks-nodegroup'), cluster: 'my-cluster' do
12
31
  it { should be_active }
13
32
  end
14
33
  ```
34
+
35
+ ### be_ready
36
+
37
+ This matcher *might* not be exactly you are expecting: it is different from what
38
+ you can see when looking at the AWS console at the Node Groups configuration
39
+ and check if the nodes Status is "Ready".
40
+
41
+ What you seeing over there is
42
+ [actually the same thing](https://aws.amazon.com/premiumsupport/knowledge-center/eks-node-status-ready/)
43
+ you would if using `kubectl`.
44
+
45
+ This matcher cannot do the same because it would involve using the Kubernetes
46
+ API: the AWS Ruby SDK currently doesn't expose this information.
47
+
48
+ What you can get from `be_ready` matcher is asserting that you have **at least**
49
+ the number of EC2 instances (the nodes in your EKS Node Group) are actually
50
+ in running state. It doesn't mean everything is fine, the node (EC2 instance)
51
+ can be running but without communication with the cluster or any order issue
52
+ regarding the Kubernetes configuration.
53
+
54
+ Although it might look an incomplete assertion, definitely the Node Group
55
+ "Status" won't be "Active" if the EC2 instances associated with it are not
56
+ running.
57
+
58
+ So, using this assertion like the sample below:
59
+
60
+ ```ruby
61
+ describe eks('my-eks-nodegroup'), cluster: 'my-cluster' do
62
+ it { should be_ready }
63
+ end
64
+ ```
65
+
66
+ Will pass if at least the minimum expected (see `scaling_config`) number of EC2
67
+ instances are running.
@@ -836,7 +836,7 @@ describe directconnect_virtual_interface('my-directconnect-virtual-interface') d
836
836
  end
837
837
  ```
838
838
 
839
- ### its(:owner_account), its(:virtual_interface_id), its(:location), its(:connection_id), its(:virtual_interface_type), its(:virtual_interface_name), its(:vlan), its(:asn), its(:amazon_side_asn), its(:auth_key), its(:amazon_address), its(:customer_address), its(:address_family), its(:virtual_interface_state), its(:customer_router_config), its(:mtu), its(:jumbo_frame_capable), its(:virtual_gateway_id), its(:direct_connect_gateway_id), its(:route_filter_prefixes), its(:bgp_peers), its(:region), its(:aws_device_v2), its(:tags)
839
+ ### its(:owner_account), its(:virtual_interface_id), its(:location), its(:connection_id), its(:virtual_interface_type), its(:virtual_interface_name), its(:vlan), its(:asn), its(:amazon_side_asn), its(:auth_key), its(:amazon_address), its(:customer_address), its(:address_family), its(:virtual_interface_state), its(:customer_router_config), its(:mtu), its(:jumbo_frame_capable), its(:virtual_gateway_id), its(:direct_connect_gateway_id), its(:route_filter_prefixes), its(:bgp_peers), its(:region), its(:aws_device_v2), its(:aws_logical_device_id), its(:tags)
840
840
  ## <a name="dynamodb_table">dynamodb_table</a>
841
841
 
842
842
  DynamodbTable resource type.
@@ -1370,9 +1370,53 @@ describe eks_nodegroup('my-eks-nodegroup'), cluster: 'my-cluster' do
1370
1370
  end
1371
1371
  ```
1372
1372
 
1373
+
1373
1374
  ### be_active, be_inactive
1374
1375
 
1375
- ### its(:nodegroup_name), its(:nodegroup_arn), its(:cluster_name), its(:version), its(:release_version), its(:created_at), its(:modified_at), its(:status), its(:capacity_type), its(:scaling_config), its(:instance_types), its(:subnets), its(:remote_access), its(:ami_type), its(:node_role), its(:labels), its(:taints), its(:resources), its(:disk_size), its(:health), its(:update_config), its(:launch_template), its(:tags)
1376
+ ### be_ready
1377
+
1378
+ This matcher *might* not be exactly you are expecting: it is different from what
1379
+ you can see when looking at the AWS console at the Node Groups configuration
1380
+ and check if the nodes Status is "Ready".
1381
+
1382
+ What you seeing over there is
1383
+ [actually the same thing](https://aws.amazon.com/premiumsupport/knowledge-center/eks-node-status-ready/)
1384
+ you would if using `kubectl`.
1385
+
1386
+ This matcher cannot do the same because it would involve using the Kubernetes
1387
+ API: the AWS Ruby SDK currently doesn't expose this information.
1388
+
1389
+ What you can get from `be_ready` matcher is asserting that you have **at least**
1390
+ the number of EC2 instances (the nodes in your EKS Node Group) are actually
1391
+ in running state. It doesn't mean everything is fine, the node (EC2 instance)
1392
+ can be running but without communication with the cluster or any order issue
1393
+ regarding the Kubernetes configuration.
1394
+
1395
+ Although it might look an incomplete assertion, definitely the Node Group
1396
+ "Status" won't be "Active" if the EC2 instances associated with it are not
1397
+ running.
1398
+
1399
+ So, using this assertion like the sample below:
1400
+
1401
+ ```ruby
1402
+ describe eks('my-eks-nodegroup'), cluster: 'my-cluster' do
1403
+ it { should be_ready }
1404
+ end
1405
+ ```
1406
+
1407
+ Will pass if at least the minimum expected (see `scaling_config`) number of EC2
1408
+ instances are running.
1409
+
1410
+ ### have_security_group
1411
+
1412
+ ```ruby
1413
+ describe eks_nodegroup('my-eks-nodegroup'), cluster: 'my-cluster' do
1414
+ it { should have_security_group('sg-1a2b3cd4') }
1415
+ end
1416
+ ```
1417
+
1418
+
1419
+ ### its(:nodegroup_name), its(:nodegroup_arn), its(:cluster_name), its(:version), its(:release_version), its(:created_at), its(:modified_at), its(:status), its(:capacity_type), its(:instance_types), its(:subnets), its(:remote_access), its(:ami_type), its(:node_role), its(:labels), its(:taints), its(:resources), its(:disk_size), its(:health), its(:update_config), its(:launch_template), its(:tags)
1376
1420
  ## <a name="elasticache">elasticache</a>
1377
1421
 
1378
1422
  Elasticache resource type.
@@ -2573,7 +2617,7 @@ describe network_interface('eni-12ab3cde') do
2573
2617
  end
2574
2618
  ```
2575
2619
 
2576
- ### its(:association), its(:availability_zone), its(:description), its(:interface_type), its(:ipv_6_addresses), its(:mac_address), its(:network_interface_id), its(:outpost_arn), its(:owner_id), its(:private_dns_name), its(:private_ip_address), its(:requester_id), its(:requester_managed), its(:source_dest_check), its(:status), its(:subnet_id), its(:vpc_id)
2620
+ ### its(:association), its(:availability_zone), its(:description), its(:interface_type), its(:ipv_6_addresses), its(:mac_address), its(:network_interface_id), its(:outpost_arn), its(:owner_id), its(:private_dns_name), its(:private_ip_address), its(:ipv_4_prefixes), its(:ipv_6_prefixes), its(:requester_id), its(:requester_managed), its(:source_dest_check), its(:status), its(:subnet_id), its(:vpc_id)
2577
2621
  ## <a name="nlb">nlb</a>
2578
2622
 
2579
2623
  NLB resource type.
@@ -2801,7 +2845,7 @@ end
2801
2845
  ```
2802
2846
 
2803
2847
 
2804
- ### its(:vpc_id), its(:db_instance_identifier), its(:db_instance_class), its(:engine), its(:db_instance_status), its(:master_username), its(:db_name), its(:endpoint), its(:allocated_storage), its(:instance_create_time), its(:preferred_backup_window), its(:backup_retention_period), its(:db_security_groups), its(:availability_zone), its(:preferred_maintenance_window), its(:pending_modified_values), its(:latest_restorable_time), its(:multi_az), its(:engine_version), its(:auto_minor_version_upgrade), its(:read_replica_source_db_instance_identifier), its(:read_replica_db_instance_identifiers), its(:read_replica_db_cluster_identifiers), its(:replica_mode), its(:license_model), its(:iops), its(:character_set_name), its(:nchar_character_set_name), its(:secondary_availability_zone), its(:publicly_accessible), its(:status_infos), its(:storage_type), its(:tde_credential_arn), its(:db_instance_port), its(:db_cluster_identifier), its(:storage_encrypted), its(:kms_key_id), its(:dbi_resource_id), its(:ca_certificate_identifier), its(:domain_memberships), its(:copy_tags_to_snapshot), its(:monitoring_interval), its(:enhanced_monitoring_resource_arn), its(:monitoring_role_arn), its(:promotion_tier), its(:db_instance_arn), its(:timezone), its(:iam_database_authentication_enabled), its(:performance_insights_enabled), its(:performance_insights_kms_key_id), its(:performance_insights_retention_period), its(:enabled_cloudwatch_logs_exports), its(:processor_features), its(:deletion_protection), its(:associated_roles), its(:listener_endpoint), its(:max_allocated_storage), its(:tag_list), its(:db_instance_automated_backups_replications), its(:customer_owned_ip_enabled), its(:aws_backup_recovery_point_arn), its(:activity_stream_status), its(:activity_stream_kms_key_id), its(:activity_stream_kinesis_stream_name), its(:activity_stream_mode), its(:activity_stream_engine_native_audit_fields_included)
2848
+ ### its(:vpc_id), its(:db_instance_identifier), its(:db_instance_class), its(:engine), its(:db_instance_status), its(:automatic_restart_time), its(:master_username), its(:db_name), its(:endpoint), its(:allocated_storage), its(:instance_create_time), its(:preferred_backup_window), its(:backup_retention_period), its(:db_security_groups), its(:availability_zone), its(:preferred_maintenance_window), its(:pending_modified_values), its(:latest_restorable_time), its(:multi_az), its(:engine_version), its(:auto_minor_version_upgrade), its(:read_replica_source_db_instance_identifier), its(:read_replica_db_instance_identifiers), its(:read_replica_db_cluster_identifiers), its(:replica_mode), its(:license_model), its(:iops), its(:character_set_name), its(:nchar_character_set_name), its(:secondary_availability_zone), its(:publicly_accessible), its(:status_infos), its(:storage_type), its(:tde_credential_arn), its(:db_instance_port), its(:db_cluster_identifier), its(:storage_encrypted), its(:kms_key_id), its(:dbi_resource_id), its(:ca_certificate_identifier), its(:domain_memberships), its(:copy_tags_to_snapshot), its(:monitoring_interval), its(:enhanced_monitoring_resource_arn), its(:monitoring_role_arn), its(:promotion_tier), its(:db_instance_arn), its(:timezone), its(:iam_database_authentication_enabled), its(:performance_insights_enabled), its(:performance_insights_kms_key_id), its(:performance_insights_retention_period), its(:enabled_cloudwatch_logs_exports), its(:processor_features), its(:deletion_protection), its(:associated_roles), its(:listener_endpoint), its(:max_allocated_storage), its(:tag_list), its(:db_instance_automated_backups_replications), its(:customer_owned_ip_enabled), its(:aws_backup_recovery_point_arn), its(:activity_stream_status), its(:activity_stream_kms_key_id), its(:activity_stream_kinesis_stream_name), its(:activity_stream_mode), its(:activity_stream_engine_native_audit_fields_included)
2805
2849
  ### :unlock: Advanced use
2806
2850
 
2807
2851
  `rds` can use `Aws::RDS::DBInstance` resource (see http://docs.aws.amazon.com/sdkforruby/api/Aws/RDS/DBInstance.html).
@@ -23,7 +23,11 @@ module Awspec::Generator
23
23
  metric_filters = select_all_cloudwatch_logs_metric_filter(log_group)
24
24
  metric_filter_lines = []
25
25
  metric_filters.each do |metric_filter|
26
- line = "it { should have_metric_filter('#{metric_filter.filter_name}') }"
26
+ line = "it { should have_metric_filter('#{metric_filter.filter_name}')"
27
+ unless metric_filter.filter_pattern.empty?
28
+ line += ".filter_pattern('#{metric_filter.filter_pattern}')"
29
+ end
30
+ line += ' }'
27
31
  metric_filter_lines.push(line)
28
32
  end
29
33
  metric_filter_lines
@@ -3,24 +3,48 @@ module Awspec::Helper
3
3
  module Ec2
4
4
  def find_ec2(id)
5
5
  # instance_id or tag:Name
6
- begin
7
- res = ec2_client.describe_instances({
8
- instance_ids: [id]
9
- })
10
- rescue Aws::EC2::Errors::InvalidInstanceIDNotFound, Aws::EC2::Errors::InvalidInstanceIDMalformed => e
11
- res = ec2_client.describe_instances({
12
- filters: [{ name: 'tag:Name', values: [id] }]
13
- })
14
- end
15
- # rubocop:enable Style/GuardClause
16
-
17
- if res.reservations.count == 0
18
- nil
19
- elsif res.reservations.count == 1
20
- res.reservations.first.instances.single_resource(id)
21
- elsif res.reservations.count > 1
22
- raise Awspec::DuplicatedResourceTypeError, "Duplicate instances matching id or tag #{id}"
6
+
7
+ # First tries to search by using an educated guess, based on the
8
+ # references below:
9
+ # https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/resource-ids.html
10
+ # https://docs.chef.io/inspec/resources/aws_ec2_instance/
11
+ # This should be faster then just first trying ID when the parameter is
12
+ # clearly not one
13
+
14
+ # https://medium.com/@Bakku1505/ruby-start-with-end-with-vs-regular-expressions-59728be0859e
15
+ if id.start_with?('i-') && id.length == 19 && id =~ /^i-[0-9a-f]/
16
+ begin
17
+ res = ec2_client.describe_instances({
18
+ instance_ids: [id]
19
+ })
20
+ rescue Aws::EC2::Errors::InvalidInstanceIDNotFound, Aws::EC2::Errors::InvalidInstanceIDMalformed => e
21
+ res = ec2_client.describe_instances({
22
+ filters: [{ name: 'tag:Name', values: [id] }]
23
+ })
24
+ end
25
+ else
26
+ begin
27
+ res = ec2_client.describe_instances({
28
+ filters: [{ name: 'tag:Name', values: [id] }]
29
+ })
30
+ rescue Aws::EC2::Errors::InvalidInstanceIDNotFound, Aws::EC2::Errors::InvalidInstanceIDMalformed => e
31
+ res = ec2_client.describe_instances({
32
+ instance_ids: [id]
33
+ })
34
+ if res.reservations.count > 1
35
+ STDERR.puts "Warning: '#{id}' unexpectedly identified as a valid instance ID during fallback search"
36
+ end
37
+ end
23
38
  end
39
+
40
+ return nil if res.reservations.count == 0
41
+ return res.reservations.first.instances.single_resource(id) if res.reservations.count == 1
42
+ raise Awspec::DuplicatedResourceTypeError, dup_ec2_instance(id) if res.reservations.count > 1
43
+ raise "Unexpected condition of having reservations = #{res.reservations.count}"
44
+ end
45
+
46
+ def dup_ec2_instance(id)
47
+ "Duplicate instances matching id or tag #{id}"
24
48
  end
25
49
 
26
50
  def find_ec2_attribute(id, attribute)
@@ -36,7 +36,7 @@ module Awspec::Helper
36
36
  # deprecated method
37
37
  def find_ecs_container_instances(cluster, container_instances)
38
38
  res = ecs_client.describe_container_instances(cluster: cluster, container_instances: container_instances)
39
- res.container_instances if res.container_instances
39
+ res.container_instances if res.container_instances # rubocop:disable Style/UnneededCondition
40
40
  end
41
41
 
42
42
  alias_method :list_ecs_container_instances, :select_ecs_container_instance_arn_by_cluster_name # deprecated method
@@ -4,6 +4,9 @@ require 'awspec/matcher/belong_to_subnet'
4
4
  require 'awspec/matcher/have_tag'
5
5
  require 'awspec/matcher/have_network_interface'
6
6
 
7
+ # EKS
8
+ require 'awspec/matcher/belong_to_subnets'
9
+
7
10
  # RDS
8
11
  require 'awspec/matcher/belong_to_db_subnet_group'
9
12
  require 'awspec/matcher/have_db_parameter_group'
@@ -53,6 +56,7 @@ require 'awspec/matcher/have_rule'
53
56
 
54
57
  # CloudWatch Logs
55
58
  require 'awspec/matcher/have_subscription_filter'
59
+ require 'awspec/matcher/have_metric_filter'
56
60
 
57
61
  # DynamoDB
58
62
  require 'awspec/matcher/have_attribute_definition'
@@ -0,0 +1,14 @@
1
+ RSpec::Matchers.define :belong_to_subnets do |*subnets|
2
+ match do |nodegroup|
3
+ superset = Set.new(subnets)
4
+ nodegroup.subnets.subset?(superset)
5
+ end
6
+ failure_message { |nodegroup| super() + failure_reason(nodegroup) }
7
+ failure_message_when_negated { |nodegroup| super() + failure_reason(nodegroup) }
8
+ end
9
+
10
+ private
11
+
12
+ def failure_reason(nodegroup)
13
+ ", but the nodes are allocated to the subnets #{nodegroup.subnets.to_a}"
14
+ end
@@ -0,0 +1,9 @@
1
+ RSpec::Matchers.define :have_metric_filter do |filter_name|
2
+ match do |log_group_name|
3
+ log_group_name.has_metric_filter?(filter_name, @pattern)
4
+ end
5
+
6
+ chain :filter_pattern do |pattern|
7
+ @pattern = pattern
8
+ end
9
+ end
data/lib/awspec/setup.rb CHANGED
@@ -18,7 +18,7 @@ EOF
18
18
  dir = 'spec'
19
19
  if File.exist? dir
20
20
  unless File.directory? dir
21
- $stderr.puts '!! #{dir} already exists and is not a directory'
21
+ $stderr.puts "!! #{dir} already exists and is not a directory"
22
22
  end
23
23
  else
24
24
  FileUtils.mkdir dir
@@ -18,7 +18,8 @@ Aws.config[:cloudwatchlogs] = {
18
18
  describe_metric_filters: {
19
19
  metric_filters: [
20
20
  {
21
- filter_name: 'my-cloudwatch-logs-metric-filter'
21
+ filter_name: 'my-cloudwatch-logs-metric-filter',
22
+ filter_pattern: '[date, error]'
22
23
  }
23
24
  ]
24
25
  },
@@ -9,8 +9,68 @@ Aws.config[:eks] = {
9
9
  nodegroup_arn: 'arn:aws:eks:us-west-2:012345678910:nodegroup/my-cluster/my-nodegroup/08bd000a',
10
10
  created_at: Time.parse('2018-10-28 00:23:32 -0400'),
11
11
  node_role: 'arn:aws:iam::012345678910:role/eks-nodegroup-role',
12
- status: 'ACTIVE'
12
+ status: 'ACTIVE',
13
+ scaling_config: { min_size: 1, desired_size: 2, max_size: 3 }
13
14
  }
14
15
  }
15
16
  }
16
17
  }
18
+
19
+ Aws.config[:ec2] = {
20
+ stub_responses: {
21
+ describe_instances: {
22
+ reservations: [
23
+ {
24
+ instances: [
25
+ {
26
+ instance_id: 'i-ec12345a',
27
+ image_id: 'ami-abc12def',
28
+ vpc_id: 'vpc-ab123cde',
29
+ subnet_id: 'subnet-1234a567',
30
+ public_ip_address: '123.0.456.789',
31
+ private_ip_address: '10.0.1.1',
32
+ instance_type: 't2.small',
33
+ state: {
34
+ name: 'running'
35
+ },
36
+ security_groups: [
37
+ {
38
+ group_id: 'sg-1a2b3cd4',
39
+ group_name: 'my-security-group-name'
40
+ }
41
+ ],
42
+ iam_instance_profile: {
43
+ arn: 'arn:aws:iam::123456789012:instance-profile/Ec2IamProfileName',
44
+ id: 'ABCDEFGHIJKLMNOPQRSTU'
45
+ },
46
+ block_device_mappings: [
47
+ {
48
+ device_name: '/dev/sda',
49
+ ebs: {
50
+ volume_id: 'vol-123a123b'
51
+ }
52
+ }
53
+ ],
54
+ network_interfaces: [
55
+ {
56
+ network_interface_id: 'eni-12ab3cde',
57
+ subnet_id: 'subnet-1234a567',
58
+ vpc_id: 'vpc-ab123cde',
59
+ attachment: {
60
+ device_index: 1
61
+ }
62
+ }
63
+ ],
64
+ tags: [
65
+ {
66
+ key: 'Name',
67
+ value: 'my-ec2'
68
+ }
69
+ ]
70
+ }
71
+ ]
72
+ }
73
+ ]
74
+ }
75
+ }
76
+ }
@@ -1,4 +1,3 @@
1
-
2
1
  Aws.config[:elasticsearchservice] = {
3
2
  stub_responses: {
4
3
  list_domain_names: {
@@ -13,9 +13,14 @@ module Awspec::Type
13
13
  return true if ret == stream_name
14
14
  end
15
15
 
16
- def has_metric_filter?(filter_name)
17
- ret = find_cloudwatch_logs_metric_fileter_by_log_group_name(@id, filter_name).filter_name
18
- return true if ret == filter_name
16
+ def has_metric_filter?(filter_name, pattern = nil)
17
+ ret = find_cloudwatch_logs_metric_fileter_by_log_group_name(@id, filter_name)
18
+ if pattern.nil?
19
+ return true if ret.filter_name == filter_name
20
+ else
21
+ return false unless ret.filter_pattern == pattern
22
+ end
23
+ return true if ret.filter_name == filter_name
19
24
  end
20
25
 
21
26
  def has_subscription_filter?(filter_name, pattern = nil)
@@ -1,10 +1,47 @@
1
+ require 'set'
2
+
1
3
  module Awspec::Type
4
+ class EksNodeEC2
5
+ attr_reader :state, :subnet_id, :sec_groups
6
+
7
+ def initialize(id, state, subnet_id, sec_groups)
8
+ @id = id
9
+ @state = state
10
+ @subnet_id = subnet_id
11
+ @sec_groups = sec_groups
12
+ end
13
+
14
+ def to_s
15
+ "ID: #{@id}, State: #{@state}, Subnet ID: #{@subnet_id}, Security Groups: #{@sec_groups}"
16
+ end
17
+ end
18
+
19
+ class EksNodeSecGroup
20
+ attr_reader :name, :id
21
+
22
+ def initialize(id, name)
23
+ @id = id
24
+ @name = name
25
+ end
26
+
27
+ def to_s
28
+ "ID: #{@id}, Name: #{@name}"
29
+ end
30
+ end
31
+
2
32
  class EksNodegroup < ResourceBase
33
+ # the tags below are standard for EKS node groups instances
34
+ EKS_CLUSTER_TAG = 'tag:eks:cluster-name'
35
+ EKS_NODEGROUP_TAG = 'tag:eks:nodegroup-name'
36
+
3
37
  attr_accessor :cluster
4
38
 
5
39
  def initialize(group_name)
6
40
  super
7
41
  @group_name = group_name
42
+ @ec2_instances = []
43
+ @sec_groups = Set.new
44
+ @sec_groups_ids = Set.new
8
45
  end
9
46
 
10
47
  def resource_via_client
@@ -19,6 +56,39 @@ module Awspec::Type
19
56
  @cluster || 'default'
20
57
  end
21
58
 
59
+ def subnets
60
+ ec2_instances = find_nodes
61
+ Set.new(ec2_instances.map { |ec2| ec2.subnet_id })
62
+ end
63
+
64
+ def has_security_group?(sec_group)
65
+ if @sec_groups.empty? || @sec_groups_ids.empty?
66
+ ec2_instances = find_nodes
67
+
68
+ ec2_instances.each do |ec2|
69
+ ec2.sec_groups.each do |sg|
70
+ @sec_groups.add(sg.name)
71
+ @sec_groups_ids.add(sg.id)
72
+ end
73
+ end
74
+ end
75
+
76
+ @sec_groups.member?(sec_group) || @sec_groups_ids.member?(sec_group)
77
+ end
78
+
79
+ def ready?
80
+ min_expected = resource_via_client.scaling_config.min_size
81
+ ec2_instances = find_nodes
82
+ running_counter = 0
83
+
84
+ ec2_instances.each do |ec2|
85
+ running_counter += 1 if ec2.state.eql?('running')
86
+ break if running_counter == min_expected
87
+ end
88
+
89
+ running_counter >= min_expected
90
+ end
91
+
22
92
  STATES = %w(ACTIVE INACTIVE)
23
93
 
24
94
  STATES.each do |state|
@@ -26,5 +96,40 @@ module Awspec::Type
26
96
  resource_via_client.status == state
27
97
  end
28
98
  end
99
+
100
+ private
101
+
102
+ def find_nodes
103
+ return @ec2_instances unless @ec2_instances.empty?
104
+
105
+ result = ec2_client.describe_instances(
106
+ {
107
+ filters: [
108
+ { name: EKS_CLUSTER_TAG, values: [cluster] },
109
+ { name: EKS_NODEGROUP_TAG, values: [@group_name] }
110
+ ]
111
+ }
112
+ )
113
+ result.reservations.each do |reservation|
114
+ reservation.instances.each do |instance|
115
+ sec_groups = []
116
+
117
+ instance.security_groups.map do |sg|
118
+ sec_groups.push(EksNodeSecGroup.new(sg.group_id, sg.group_name))
119
+ end
120
+
121
+ @ec2_instances.push(
122
+ EksNodeEC2.new(
123
+ instance.instance_id,
124
+ instance.state.name,
125
+ instance.subnet_id,
126
+ sec_groups
127
+ )
128
+ )
129
+ end
130
+ end
131
+
132
+ @ec2_instances
133
+ end
29
134
  end
30
135
  end
@@ -108,8 +108,8 @@ module Awspec::Type
108
108
  if value.is_a?(Array)
109
109
  return false if r[key].map(&:to_h) != value
110
110
  end
111
- true
112
111
  end
112
+ true
113
113
  end
114
114
  end
115
115
 
@@ -1,3 +1,3 @@
1
1
  module Awspec
2
- VERSION = '1.24.3'
2
+ VERSION = '1.24.4'
3
3
  end
metadata CHANGED
@@ -1,15 +1,29 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: awspec
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.24.3
4
+ version: 1.24.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - k1LoW
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-07-12 00:00:00.000000000 Z
11
+ date: 2021-08-09 00:00:00.000000000 Z
12
12
  dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: addressable
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
13
27
  - !ruby/object:Gem::Dependency
14
28
  name: aws-sdk
15
29
  requirement: !ruby/object:Gem::Requirement
@@ -122,20 +136,6 @@ dependencies:
122
136
  - - ">="
123
137
  - !ruby/object:Gem::Version
124
138
  version: '0'
125
- - !ruby/object:Gem::Dependency
126
- name: addressable
127
- requirement: !ruby/object:Gem::Requirement
128
- requirements:
129
- - - ">="
130
- - !ruby/object:Gem::Version
131
- version: '0'
132
- type: :runtime
133
- prerelease: false
134
- version_requirements: !ruby/object:Gem::Requirement
135
- requirements:
136
- - - ">="
137
- - !ruby/object:Gem::Version
138
- version: '0'
139
139
  - !ruby/object:Gem::Dependency
140
140
  name: bundler
141
141
  requirement: !ruby/object:Gem::Requirement
@@ -204,14 +204,14 @@ dependencies:
204
204
  requirements:
205
205
  - - "~>"
206
206
  - !ruby/object:Gem::Version
207
- version: 0.49.0
207
+ version: 0.57.0
208
208
  type: :development
209
209
  prerelease: false
210
210
  version_requirements: !ruby/object:Gem::Requirement
211
211
  requirements:
212
212
  - - "~>"
213
213
  - !ruby/object:Gem::Version
214
- version: 0.49.0
214
+ version: 0.57.0
215
215
  description: RSpec tests for your AWS resources.
216
216
  email:
217
217
  - k1lowxb@gmail.com
@@ -221,9 +221,9 @@ extensions: []
221
221
  extra_rdoc_files: []
222
222
  files:
223
223
  - ".editorconfig"
224
+ - ".github/workflows/ci.yml"
225
+ - ".github/workflows/doc.yml"
224
226
  - ".rubocop.yml"
225
- - ".tachikoma.yml"
226
- - ".travis.yml"
227
227
  - Gemfile
228
228
  - LICENSE.txt
229
229
  - README.md
@@ -539,6 +539,7 @@ files:
539
539
  - lib/awspec/matcher/belong_to_nlb.rb
540
540
  - lib/awspec/matcher/belong_to_replication_group.rb
541
541
  - lib/awspec/matcher/belong_to_subnet.rb
542
+ - lib/awspec/matcher/belong_to_subnets.rb
542
543
  - lib/awspec/matcher/belong_to_vpc.rb
543
544
  - lib/awspec/matcher/have_attribute_definition.rb
544
545
  - lib/awspec/matcher/have_cluster_parameter_group.rb
@@ -550,6 +551,7 @@ files:
550
551
  - lib/awspec/matcher/have_inline_policy.rb
551
552
  - lib/awspec/matcher/have_key_policy.rb
552
553
  - lib/awspec/matcher/have_key_schema.rb
554
+ - lib/awspec/matcher/have_metric_filter.rb
553
555
  - lib/awspec/matcher/have_network_interface.rb
554
556
  - lib/awspec/matcher/have_option_group.rb
555
557
  - lib/awspec/matcher/have_origin.rb
@@ -750,7 +752,7 @@ homepage: https://github.com/k1LoW/awspec
750
752
  licenses:
751
753
  - MIT
752
754
  metadata: {}
753
- post_install_message:
755
+ post_install_message:
754
756
  rdoc_options: []
755
757
  require_paths:
756
758
  - lib
@@ -765,8 +767,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
765
767
  - !ruby/object:Gem::Version
766
768
  version: '0'
767
769
  requirements: []
768
- rubygems_version: 3.1.4
769
- signing_key:
770
+ rubygems_version: 3.0.3
771
+ signing_key:
770
772
  specification_version: 4
771
773
  summary: RSpec tests for your AWS resources.
772
774
  test_files: []
data/.tachikoma.yml DELETED
@@ -1 +0,0 @@
1
- strategy: 'bundler'
data/.travis.yml DELETED
@@ -1,27 +0,0 @@
1
- ---
2
- language: ruby
3
- env:
4
- global:
5
- DISABLE_AWS_CLIENT_CHECK: true
6
- matrix:
7
- include:
8
- - rvm: 2.7.3
9
- env: RUBYGEMS_VERSION=
10
- - rvm: 2.6.2
11
- env: RUBYGEMS_VERSION=
12
- - rvm: 2.5.3
13
- env: RUBYGEMS_VERSION=
14
- - rvm: 2.4.5
15
- env: RUBYGEMS_VERSION=
16
- - rvm: 2.3.8
17
- env: RUBYGEMS_VERSION=
18
- - rvm: 2.2.10
19
- env: RUBYGEMS_VERSION=2.7.8
20
- - rvm: 2.1.10
21
- env: RUBYGEMS_VERSION=2.7.8
22
- before_install:
23
- - gem update --system ${RUBYGEMS_VERSION}
24
- - gem pristine bundler
25
-
26
- script:
27
- - bundle exec rake spec