ruby_aem_aws_odysseas 1.4.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.
Files changed (36) hide show
  1. checksums.yaml +7 -0
  2. data/conf/gem.yaml +1 -0
  3. data/lib/ruby_aem_aws/abstract/cloudwatch.rb +83 -0
  4. data/lib/ruby_aem_aws/abstract/component.rb +54 -0
  5. data/lib/ruby_aem_aws/abstract/grouped_component.rb +39 -0
  6. data/lib/ruby_aem_aws/abstract/single_component.rb +36 -0
  7. data/lib/ruby_aem_aws/abstract/snapshot.rb +35 -0
  8. data/lib/ruby_aem_aws/abstract/stackmanager.rb +68 -0
  9. data/lib/ruby_aem_aws/architecture/consolidated_stack.rb +49 -0
  10. data/lib/ruby_aem_aws/architecture/full_set_stack.rb +141 -0
  11. data/lib/ruby_aem_aws/architecture/stack_manager.rb +44 -0
  12. data/lib/ruby_aem_aws/client/cloudwatch.rb +87 -0
  13. data/lib/ruby_aem_aws/client/dynamo_db.rb +36 -0
  14. data/lib/ruby_aem_aws/client/s3.rb +42 -0
  15. data/lib/ruby_aem_aws/client/sns_topic.rb +30 -0
  16. data/lib/ruby_aem_aws/component/author.rb +71 -0
  17. data/lib/ruby_aem_aws/component/author_dispatcher.rb +84 -0
  18. data/lib/ruby_aem_aws/component/author_primary.rb +62 -0
  19. data/lib/ruby_aem_aws/component/author_publish_dispatcher.rb +56 -0
  20. data/lib/ruby_aem_aws/component/author_standby.rb +62 -0
  21. data/lib/ruby_aem_aws/component/chaos_monkey.rb +78 -0
  22. data/lib/ruby_aem_aws/component/component_descriptor.rb +28 -0
  23. data/lib/ruby_aem_aws/component/orchestrator.rb +78 -0
  24. data/lib/ruby_aem_aws/component/publish.rb +78 -0
  25. data/lib/ruby_aem_aws/component/publish_dispatcher.rb +83 -0
  26. data/lib/ruby_aem_aws/component/stack_manager_resources.rb +90 -0
  27. data/lib/ruby_aem_aws/constants.rb +53 -0
  28. data/lib/ruby_aem_aws/error.rb +68 -0
  29. data/lib/ruby_aem_aws/mixins/healthy_count_verifier.rb +154 -0
  30. data/lib/ruby_aem_aws/mixins/healthy_resource_verifier.rb +188 -0
  31. data/lib/ruby_aem_aws/mixins/healthy_state_verifier.rb +45 -0
  32. data/lib/ruby_aem_aws/mixins/instance_describer.rb +34 -0
  33. data/lib/ruby_aem_aws/mixins/metric_verifier.rb +189 -0
  34. data/lib/ruby_aem_aws/mixins/snapshot_verifier.rb +37 -0
  35. data/lib/ruby_aem_aws_odysseas.rb +152 -0
  36. metadata +148 -0
@@ -0,0 +1,44 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require_relative '../component/stack_manager_resources'
16
+
17
+ module RubyAemAws
18
+ # Interface to interact with AEM StackManager
19
+ class StackManager
20
+ attr_reader :sm_resources, :cloudformation_client
21
+ # @param stack_prefix AWS tag: StackPrefix
22
+ # @param params Array of AWS Clients and Resource connections:
23
+ # - CloudFormationClient: AWS Cloudformation Client.
24
+ # - CloudWatchClient: AWS Cloudwatch Client.
25
+ # - CloudWatchLogsClient: AWS Cloudwatch Logs Client.
26
+ # - DynamoDBClient: AWS DynamoDB Client.
27
+ # - S3Client: AWS S3 Client.
28
+ # - S3Resource: AWS S3 Resource connection.
29
+ # @return new RubyAemAws::StackManager instance
30
+ def initialize(stack_prefix, params)
31
+ stack_manager_aws_client = {
32
+ CloudWatchClient: params[:CloudWatchClient],
33
+ CloudWatchLogsClient: params[:CloudWatchLogsClient],
34
+ DynamoDBClient: params[:DynamoDBClient],
35
+ S3Client: params[:S3Client],
36
+ S3Resource: params[:S3Resource]
37
+ }
38
+
39
+ @sm_resources = RubyAemAws::Component::StackManagerResources.new(stack_manager_aws_client)
40
+ @cloudformation_client = params[:CloudFormationClient]
41
+ @stack_prefix = stack_prefix
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,87 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ module RubyAemAws
16
+ # Mixin for checking that an instance has associated CloudWatch metrics.
17
+ module CloudwatchClient
18
+ # @param alarm_name Cloudwatch alarm name
19
+ # @return Cloudwatch client describe_alarms response
20
+ def get_alarm(alarm_name)
21
+ alarm_filter = filter_for_cloudwatch_alarm(alarm_name)
22
+
23
+ response = cloud_watch_client.describe_alarms(alarm_filter)
24
+
25
+ until response.next_token.nil?
26
+ next_token = { next_token: response.next_token }
27
+ filter.update(next_token)
28
+ response = cloud_watch_client.describe_alarms(alarm_filter)
29
+ end
30
+
31
+ response
32
+ end
33
+
34
+ # @param loggroup_name Cloudwatch loggroup name
35
+ # @param log_stream_name Cloudwatch log stream name
36
+ # @param log_message Log message to filter for
37
+ # @return Cloudwatch log client filter_log_events response
38
+ def get_log_event(loggroup_name, log_stream_name, log_message)
39
+ filter = filter_for_cloudwatch_log_event(loggroup_name, log_stream_name, log_message)
40
+ response = cloud_watch_log_client.filter_log_events(filter)
41
+
42
+ until response.next_token.nil?
43
+ next_token = { next_token: response.next_token }
44
+ filter.update(next_token)
45
+ response = cloud_watch_client.filter_log_events(filter)
46
+ end
47
+
48
+ response
49
+ end
50
+
51
+ # @param loggroup_name Cloudwatch loggroup name
52
+ # @param log_stream_name Cloudwatch log stream name
53
+ # @return Cloudwatch log client describe_log_streams response
54
+ def get_log_streams(loggroup_name, log_stream_name)
55
+ filter = filter_for_cloudwatch_log_stream(loggroup_name, log_stream_name)
56
+
57
+ response = cloud_watch_log_client.describe_log_streams(filter)
58
+
59
+ until response.next_token.nil?
60
+ next_token = { next_token: response.next_token }
61
+ filter.update(next_token)
62
+ response = cloud_watch_client.describe_log_streams(filter)
63
+ end
64
+
65
+ response
66
+ end
67
+
68
+ # @param namespace Cloudwatch namespace name
69
+ # @param metric_name Cloudwatch metric name
70
+ # @param dimension Cloudwatch dimension filter
71
+ # @return Cloudwatch client list_metrics response
72
+ def get_metrics(namespace, metric_name, dimension)
73
+ filter = filter_for_cloudwatch_metric(namespace, metric_name)
74
+ filter.update(dimension)
75
+
76
+ response = cloud_watch_client.list_metrics(filter)
77
+
78
+ until response.next_token.nil?
79
+ next_token = { next_token: response.next_token }
80
+ filter.update(next_token)
81
+ response = cloud_watch_client.list_metrics(filter)
82
+ end
83
+
84
+ response
85
+ end
86
+ end
87
+ end
@@ -0,0 +1,36 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ module RubyAemAws
16
+ # Mixin for interaction with AWS DynamoDB
17
+ module DynamoDB
18
+ # @param filter Filter to scan for
19
+ # @return scanned attribute
20
+ def scan(filter)
21
+ # We need to give AWS time to update the DynamoDB
22
+ # consistent_read seems not to work everytime
23
+ sleep 5
24
+ dynamodb_client.scan(filter)
25
+ end
26
+
27
+ # @param filter Filter to query for
28
+ # @return queried attribute
29
+ def query(filter)
30
+ # We need to give AWS time to update the DynamoDB
31
+ # consistent_read seems not to work everytime
32
+ sleep 5
33
+ dynamodb_client.query(filter)
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,42 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ module RubyAemAws
16
+ # Mixin for interaction with AWS S3
17
+ module S3Access
18
+ # @param bucket AWS S3 bucket name
19
+ # @return AWS S3 resource bucket connection
20
+ def get_s3_bucket(bucket)
21
+ s3_resource.bucket(bucket)
22
+ end
23
+
24
+ # @param bucket AWS S3 bucket name
25
+ # @param s3_object_name AWS S3 object name
26
+ # @return S3 object
27
+ def get_s3_bucket_object(bucket, s3_object_name)
28
+ bucket = get_s3_bucket(bucket)
29
+ bucket.object(s3_object_name)
30
+ end
31
+
32
+ # @param bucket AWS S3 bucket name
33
+ # @param s3_object_name AWS S3 object name
34
+ # @param dest_path Download destionation path
35
+ # @return S3 object
36
+ def get_s3_object(bucket, s3_object_name, dest_path)
37
+ options = { bucket: bucket, key: s3_object_name }
38
+ options = options.merge(response_target: dest_path) unless dest_path.nil?
39
+ s3_client.get_object(options)
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,30 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ module RubyAemAws
16
+ # Mixin for interaction with AWS SNS
17
+ module SNSTopic
18
+ # @param topicarn the ARN of the SNS Topix to publish the message
19
+ # @param message the SNS Message to publish
20
+ # @return Message ID
21
+ def publish(topicarn, message)
22
+ client = Aws::SNS::Topic.new(topicarn)
23
+ sns_message = { subject: 'Publish',
24
+ message: message,
25
+ message_structure: 'json' }
26
+ publish = client.publish(sns_message)
27
+ publish.message_id
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,71 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require_relative 'author_primary'
16
+ require_relative 'author_standby'
17
+
18
+ module RubyAemAws
19
+ module Component
20
+ # Interface to the AWS instances running the Author components of a full-set AEM stack.
21
+ class Author
22
+ attr_reader :author_primary, :author_standby
23
+
24
+ ELB_ID = 'AuthorLoadBalancer'.freeze
25
+ ELB_NAME = 'AEM Author Load Balancer'.freeze
26
+
27
+ # @param stack_prefix AWS tag: StackPrefix
28
+ # @param params Array of AWS Clients and Resource connections:
29
+ # - CloudWatchClient: AWS Cloudwatch Client.
30
+ # - CloudWatchLogsClient: AWS Cloudwatch Logs Client.
31
+ # - Ec2Resource: AWS EC2 Resource connection.
32
+ # - ElbClient: AWS ElasticLoadBalancer Client.
33
+ # @return new RubyAemAws::FullSet::Author
34
+ def initialize(stack_prefix, params)
35
+ author_aws_clients = {
36
+ CloudWatchClient: params[:CloudWatchClient],
37
+ CloudWatchLogsClient: params[:CloudWatchLogsClient],
38
+ Ec2Resource: params[:Ec2Resource]
39
+ }
40
+
41
+ @author_primary = Component::AuthorPrimary.new(stack_prefix, author_aws_clients)
42
+ @author_standby = Component::AuthorStandby.new(stack_prefix, author_aws_clients)
43
+ @ec2_resource = params[:Ec2Resource]
44
+ @elb_client = params[:ElbClient]
45
+ end
46
+
47
+ # @return true, if all author instances are healthy
48
+ def healthy?
49
+ instance = 0
50
+ instance += 1 if author_primary.healthy?
51
+ instance += 1 if author_standby.healthy?
52
+ return true unless instance < 2
53
+ end
54
+
55
+ # @return true, if all author instances are healthy
56
+ def wait_until_healthy
57
+ instance = 0
58
+ instance += 1 if author_primary.wait_until_healthy.eql? true
59
+ instance += 1 if author_standby.wait_until_healthy.eql? true
60
+ return true unless instance < 2
61
+ end
62
+
63
+ def get_tags
64
+ tags = []
65
+ tags.push(author_primary.get_tags)
66
+ tags.push(author_standby.get_tags)
67
+ tags
68
+ end
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,84 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require_relative '../abstract/grouped_component'
16
+ require_relative '../abstract/snapshot'
17
+ require_relative '../constants'
18
+ require_relative '../mixins/healthy_resource_verifier'
19
+ require_relative '../mixins/metric_verifier'
20
+ require_relative 'component_descriptor'
21
+ require_relative '../mixins/snapshot_verifier'
22
+
23
+ module RubyAemAws
24
+ module Component
25
+ # Interface to the AWS instances playing and supporting the AuthorDispatcher role in a full-set AEM stack.
26
+ class AuthorDispatcher
27
+ attr_reader :descriptor, :ec2_resource, :asg_client, :elb_client, :cloud_watch_client, :cloud_watch_log_client
28
+ include AbstractGroupedComponent
29
+ include AbstractSnapshot
30
+ include HealthyResourceVerifier
31
+ include MetricVerifier
32
+ include SnapshotVerifier
33
+
34
+ EC2_COMPONENT = 'author-dispatcher'.freeze
35
+ EC2_NAME = 'AEM Author Dispatcher'.freeze
36
+ ELB_ID = 'AuthorDispatcherLoadBalancer'.freeze
37
+ ELB_NAME = 'AEM Author Dispatcher Load Balancer'.freeze
38
+
39
+ # @param stack_prefix AWS tag: StackPrefix
40
+ # @param params Array of AWS Clients and Resource connections:
41
+ # - AutoScalingClient: AWS AutoScalingGroup Client.
42
+ # - CloudWatchClient: AWS Cloudwatch Client.
43
+ # - CloudWatchLogsClient: AWS Cloudwatch Logs Client.
44
+ # - Ec2Resource: AWS EC2 Resource connection.
45
+ # - ElbClient: AWS ElasticLoadBalancer Client.
46
+ # @return new RubyAemAws::FullSet::AuthorDispatcher
47
+ def initialize(stack_prefix, params)
48
+ @descriptor = ComponentDescriptor.new(stack_prefix,
49
+ EC2Descriptor.new(EC2_COMPONENT, EC2_NAME),
50
+ ELBDescriptor.new(ELB_ID, ELB_NAME))
51
+ @asg_client = params[:AutoScalingClient]
52
+ @cloud_watch_client = params[:CloudWatchClient]
53
+ @cloud_watch_log_client = params[:CloudWatchLogsClient]
54
+ @ec2_resource = params[:Ec2Resource]
55
+ @elb_client = params[:ElbClient]
56
+ end
57
+
58
+ def terminate_all_instances
59
+ get_all_instances.each do |i|
60
+ next if i.nil? || i.state.code != Constants::INSTANCE_STATE_CODE_RUNNING
61
+
62
+ i.terminate
63
+ i.wait_until_terminated
64
+ end
65
+ end
66
+
67
+ def terminate_random_instance
68
+ instance = get_random_instance
69
+ instance.terminate
70
+ instance.wait_until_terminated
71
+ end
72
+
73
+ def get_tags
74
+ tags = []
75
+ get_all_instances.each do |i|
76
+ next if i.nil? || i.state.code != Constants::INSTANCE_STATE_CODE_RUNNING
77
+
78
+ tags.push(i.tags)
79
+ end
80
+ tags
81
+ end
82
+ end
83
+ end
84
+ end
@@ -0,0 +1,62 @@
1
+ # Copyright 2018 Shine Solutions
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require_relative '../abstract/single_component'
16
+ require_relative '../abstract/snapshot'
17
+ require_relative '../mixins/healthy_state_verifier'
18
+ require_relative '../mixins/metric_verifier'
19
+ require_relative '../mixins/snapshot_verifier'
20
+
21
+ module RubyAemAws
22
+ module Component
23
+ # Interface to the AWS instance running the Author-Primary component of a full-set AEM stack.
24
+ class AuthorPrimary
25
+ attr_reader :descriptor, :ec2_resource, :cloud_watch_client, :cloud_watch_log_client
26
+ include AbstractSingleComponent
27
+ include AbstractSnapshot
28
+ include HealthyStateVerifier
29
+ include MetricVerifier
30
+ include SnapshotVerifier
31
+
32
+ EC2_COMPONENT = 'author-primary'.freeze
33
+ EC2_NAME = 'AEM Author - Primary'.freeze
34
+
35
+ # @param stack_prefix AWS tag: StackPrefix
36
+ # @param params Array of AWS Clients and Resource connections:
37
+ # - CloudWatchClient: AWS Cloudwatch Client.
38
+ # - CloudWatchLogsClient: AWS Cloudwatch Logs Client.
39
+ # - Ec2Resource: AWS EC2 Resource connection.
40
+ # @return new RubyAemAws::FullSet::AuthorPrimary
41
+ def initialize(stack_prefix, params)
42
+ @descriptor = ComponentDescriptor.new(stack_prefix,
43
+ EC2Descriptor.new(EC2_COMPONENT, EC2_NAME))
44
+ @cloud_watch_client = params[:CloudWatchClient]
45
+ @cloud_watch_log_client = params[:CloudWatchLogsClient]
46
+ @ec2_resource = params[:Ec2Resource]
47
+ end
48
+
49
+ # @return Aws::EC2::Instance
50
+ def terminate
51
+ instance = get_instance
52
+ instance.terminate
53
+ instance.wait_until_terminated
54
+ end
55
+
56
+ def get_tags
57
+ instance = get_instance
58
+ instance.tags
59
+ end
60
+ end
61
+ end
62
+ end