示例#1
0
        internal DescribeStackEventsResponse DescribeStackEvents(DescribeStackEventsRequest request)
        {
            var marshaller   = new DescribeStackEventsRequestMarshaller();
            var unmarshaller = DescribeStackEventsResponseUnmarshaller.Instance;

            return(Invoke <DescribeStackEventsRequest, DescribeStackEventsResponse>(request, marshaller, unmarshaller));
        }
        /// <summary>
        /// <para> Returns all the stack related events for the AWS account. If <c>StackName</c> is specified, returns events related to all the stacks
        /// with the given name. If <c>StackName</c> is not specified, returns all the events for the account. For more information about a stack's
        /// event history, go to the AWS CloudFormation User Guide. </para> <para><b>NOTE:</b>Events are returned, even if the stack never existed or
        /// has been successfully deleted.</para>
        /// </summary>
        ///
        /// <param name="describeStackEventsRequest">Container for the necessary parameters to execute the DescribeStackEvents service method on
        ///           AmazonCloudFormation.</param>
        ///
        /// <returns>The response from the DescribeStackEvents service method, as returned by AmazonCloudFormation.</returns>
        ///
        public DescribeStackEventsResponse DescribeStackEvents(DescribeStackEventsRequest describeStackEventsRequest)
        {
            IRequest <DescribeStackEventsRequest> request  = new DescribeStackEventsRequestMarshaller().Marshall(describeStackEventsRequest);
            DescribeStackEventsResponse           response = Invoke <DescribeStackEventsRequest, DescribeStackEventsResponse> (request, this.signer, DescribeStackEventsResponseUnmarshaller.GetInstance());

            return(response);
        }
示例#3
0
        /// <summary>
        /// Initiates the asynchronous execution of the DescribeStackEvents operation.
        /// <seealso cref="Amazon.CloudFormation.IAmazonCloudFormation.DescribeStackEvents"/>
        /// </summary>
        ///
        /// <param name="request">Container for the necessary parameters to execute the DescribeStackEvents operation.</param>
        /// <param name="cancellationToken">
        ///     A cancellation token that can be used by other objects or threads to receive notice of cancellation.
        /// </param>
        /// <returns>The task object representing the asynchronous operation.</returns>
        public Task <DescribeStackEventsResponse> DescribeStackEventsAsync(DescribeStackEventsRequest request, CancellationToken cancellationToken = default(CancellationToken))
        {
            var marshaller   = new DescribeStackEventsRequestMarshaller();
            var unmarshaller = DescribeStackEventsResponseUnmarshaller.GetInstance();

            return(Invoke <IRequest, DescribeStackEventsRequest, DescribeStackEventsResponse>(request, marshaller, unmarshaller, signer, cancellationToken));
        }
        public override void Invoke(AWSCredentials creds, RegionEndpoint region, int maxItems)
        {
            AmazonCloudFormationConfig config = new AmazonCloudFormationConfig();

            config.RegionEndpoint = region;
            ConfigureClient(config);
            AmazonCloudFormationClient client = new AmazonCloudFormationClient(creds, config);

            DescribeStackEventsResponse resp = new DescribeStackEventsResponse();

            do
            {
                DescribeStackEventsRequest req = new DescribeStackEventsRequest
                {
                    NextToken = resp.NextToken
                };

                resp = client.DescribeStackEvents(req);
                CheckError(resp.HttpStatusCode, "200");

                foreach (var obj in resp.StackEvents)
                {
                    AddObject(obj);
                }
            }while (!string.IsNullOrEmpty(resp.NextToken));
        }
示例#5
0
        /// <summary>
        /// Initiates the asynchronous execution of the DescribeStackEvents operation.
        /// </summary>
        ///
        /// <param name="request">Container for the necessary parameters to execute the DescribeStackEvents operation.</param>
        /// <param name="cancellationToken">
        ///     A cancellation token that can be used by other objects or threads to receive notice of cancellation.
        /// </param>
        /// <returns>The task object representing the asynchronous operation.</returns>
        public Task <DescribeStackEventsResponse> DescribeStackEventsAsync(DescribeStackEventsRequest request, System.Threading.CancellationToken cancellationToken = default(CancellationToken))
        {
            var marshaller   = new DescribeStackEventsRequestMarshaller();
            var unmarshaller = DescribeStackEventsResponseUnmarshaller.Instance;

            return(InvokeAsync <DescribeStackEventsRequest, DescribeStackEventsResponse>(request, marshaller,
                                                                                         unmarshaller, cancellationToken));
        }
示例#6
0
        private async Task ReadNewEventsAsync()
        {
            var stackEvents = new List <StackEvent>();

            var describeStackEventsRequest = new DescribeStackEventsRequest {
                StackName = _stackName
            };
            var listStacksPaginator = _cloudFormationClient.Paginators.DescribeStackEvents(describeStackEventsRequest);

            try
            {
                var breakPaginator = false;
                await foreach (var response in listStacksPaginator.Responses)
                {
                    foreach (var stackEvent in response?.StackEvents ?? new List <StackEvent>())
                    {
                        // Event from before we are interested in
                        if (stackEvent.Timestamp < _startTime)
                        {
                            breakPaginator = true;
                            break;
                        }

                        // Already processed event
                        if (_processedEventIds.Contains(stackEvent.EventId))
                        {
                            breakPaginator = true;
                            break;
                        }

                        // New event, save it
                        _processedEventIds.Add(stackEvent.EventId);
                        stackEvents.Add(stackEvent);
                    }

                    if (breakPaginator)
                    {
                        break;
                    }
                }
            }
            catch (AmazonCloudFormationException exception) when(exception.ErrorCode.Equals("ValidationError") && exception.Message.Equals($"Stack [{_stackName}] does not exist"))
            {
                // Stack is deleted, there could be some missed events between the last poll timestamp and DELETE_COMPLETE
            }
            catch (AmazonCloudFormationException)
            {
                // Other AmazonCloudFormationException
            }

            foreach (var stackEvent in stackEvents.OrderBy(e => e.Timestamp))
            {
                var row = new[]
示例#7
0
        /// <summary>
        /// <para>Returns all stack related events for a specified stack. For more information about a stack's event history, go to <a href="http://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/concept-stack.html">Stacks</a> in the AWS CloudFormation User
        /// Guide.</para> <para><b>NOTE:</b>Events are returned, even if the stack never existed or has been successfully deleted.</para>
        /// </summary>
        ///
        /// <param name="request">Container for the necessary parameters to execute the DescribeStackEvents service method on
        /// AmazonCloudFormation.</param>
        ///
        /// <returns>The response from the DescribeStackEvents service method, as returned by AmazonCloudFormation.</returns>
        public DescribeStackEventsResponse DescribeStackEvents(DescribeStackEventsRequest request)
        {
            var task = DescribeStackEventsAsync(request);

            try
            {
                return(task.Result);
            }
            catch (AggregateException e)
            {
                ExceptionDispatchInfo.Capture(e.InnerException).Throw();
                return(null);
            }
        }
示例#8
0
        /// <summary>
        /// 本接口(DescribeStackEvents)用于查看一个或多个事件详细信息。
        ///
        /// - 可以根据事件ID过滤感兴趣的事件
        /// - 也可以根据版本ID,资源栈ID,事件类型,事件状态过滤事件,过滤信息详细请见过滤器Filter
        /// - 如果参数为空,返回当前用户一定数量(Limit所指定的数量,默认为20)的事件
        /// </summary>
        /// <param name="req"><see cref="DescribeStackEventsRequest"/></param>
        /// <returns><see cref="DescribeStackEventsResponse"/></returns>
        public DescribeStackEventsResponse DescribeStackEventsSync(DescribeStackEventsRequest req)
        {
            JsonResponseModel <DescribeStackEventsResponse> rsp = null;

            try
            {
                var strResp = this.InternalRequestSync(req, "DescribeStackEvents");
                rsp = JsonConvert.DeserializeObject <JsonResponseModel <DescribeStackEventsResponse> >(strResp);
            }
            catch (JsonSerializationException e)
            {
                throw new TencentCloudSDKException(e.Message);
            }
            return(rsp.Response);
        }
示例#9
0
        private static async Task <List <StackEvent> > GetLatestEventsAsync(ILogger log, IAmazonCloudFormation cloudformation, string stackName, DateTime mintimeStampForEvents, string mostRecentEventId)
        {
            var noNewEvents = false;
            var events      = new List <StackEvent>();

            DescribeStackEventsResponse response = null;

            do
            {
                var request = new DescribeStackEventsRequest {
                    StackName = stackName
                };
                if (response != null)
                {
                    request.NextToken = response.NextToken;
                }

                try
                {
                    response = await cloudformation.DescribeStackEventsAsync(request).ConfigureAwait(false);
                }
                catch (Exception e)
                {
                    log.Error(e, "Error getting events for stack");
                    throw;
                }

                foreach (var evnt in response.StackEvents)
                {
                    if (string.Equals(evnt.EventId, mostRecentEventId) || evnt.Timestamp < mintimeStampForEvents)
                    {
                        noNewEvents = true;
                        break;
                    }
                    events.Add(evnt);
                }
            } while (!noNewEvents && !string.IsNullOrEmpty(response.NextToken));

            return(events);
        }
示例#10
0
        private async Task <List <StackEvent> > GetLatestEventsAsync(string stackName, DateTime mintimeStampForEvents, string mostRecentEventId)
        {
            bool noNewEvents = false;
            List <StackEvent>           events   = new List <StackEvent>();
            DescribeStackEventsResponse response = null;

            do
            {
                var request = new DescribeStackEventsRequest()
                {
                    StackName = stackName
                };
                if (response != null)
                {
                    request.NextToken = response.NextToken;
                }

                try
                {
                    response = await this.CloudFormationClient.DescribeStackEventsAsync(request);
                }
                catch (Exception e)
                {
                    throw new LambdaToolsException($"Error getting events for stack: {e.Message}", LambdaToolsException.ErrorCode.CloudFormationDescribeStackEvents, e);
                }
                foreach (var evnt in response.StackEvents)
                {
                    if (string.Equals(evnt.EventId, mostRecentEventId) || evnt.Timestamp < mintimeStampForEvents)
                    {
                        noNewEvents = true;
                        break;
                    }

                    events.Add(evnt);
                }
            } while (!noNewEvents && !string.IsNullOrEmpty(response.NextToken));

            return(events);
        }
示例#11
0
        public IEnumerable <StackEvent> GetStackEvents(Stack stack)
        {
            var request = new DescribeStackEventsRequest {
                StackName = stack.StackName
            };
            DescribeStackEventsResponse response;

            try
            {
                response = _cloudFormationClient.DescribeStackEvents(request);
            }
            catch (AmazonCloudFormationException exception)
            {
                if (exception.Message.Contains(_nonExistenceMarker))
                {
                    return(Enumerable.Empty <StackEvent>());
                }
                throw;
            }

            return(response.StackEvents);
        }
示例#12
0
        private async Task <List <StackEvent> > GetStackEvents(string?lastEventId, string stackId, DeployContext context, CancellationToken cancellationToken)
        {
            cancellationToken.ThrowIfCancellationRequested();

            var request = new DescribeStackEventsRequest {
                StackName = stackId
            };
            var response = await cloudformation.DescribeStackEventsAsync(request, cancellationToken);

            var relevantEvents = new List <StackEvent>();

            foreach (var @event in response.StackEvents)
            {
                if (@event.EventId == lastEventId || @event.Timestamp < context.Timestamp)
                {
                    break;
                }

                relevantEvents.Add(@event);
            }

            relevantEvents.Reverse();
            return(relevantEvents);
        }
示例#13
0
        private async Task <(Stack Stack, bool Success)> TrackStackUpdate(Module module, string stackId, string mostRecentStackEventId)
        {
            var seenEventIds = new HashSet <string>();
            var foundMostRecentStackEvent = (mostRecentStackEventId == null);
            var request = new DescribeStackEventsRequest {
                StackName = stackId
            };

            // iterate as long as the stack is being created/updated
            var active  = true;
            var success = false;

            while (active)
            {
                await Task.Delay(TimeSpan.FromSeconds(3));

                // fetch as many events as possible for the current stack
                var events   = new List <StackEvent>();
                var response = await module.Settings.CfClient.DescribeStackEventsAsync(request);

                events.AddRange(response.StackEvents);
                events.Reverse();

                // skip any events that preceded the most recent event before the stack update operation
                while (!foundMostRecentStackEvent && events.Any())
                {
                    var evt = events.First();
                    if (evt.EventId == mostRecentStackEventId)
                    {
                        foundMostRecentStackEvent = true;
                    }
                    seenEventIds.Add(evt.EventId);
                    events.RemoveAt(0);
                }
                if (!foundMostRecentStackEvent)
                {
                    module.Settings.AddError("unable to find starting event");
                    return(Stack : null, Success : false);
                }

                // report only on new events
                foreach (var evt in events.Where(evt => !seenEventIds.Contains(evt.EventId)))
                {
                    Console.WriteLine($"{evt.ResourceStatus,-35} {evt.ResourceType,-55} {evt.LogicalResourceId}{(evt.ResourceStatusReason != null ? $" ({evt.ResourceStatusReason})" : "")}");
                    if (!seenEventIds.Add(evt.EventId))
                    {
                        // we found an event we already saw in the past, no point in looking at more events
                        break;
                    }
                    if (IsFinalStackEvent(evt))
                    {
                        // event signals stack creation/update completion; time to stop
                        active  = false;
                        success = IsSuccessfulFinalStackEvent(evt);
                        break;
                    }
                }
            }

            // describe stack and report any output values
            var description = await module.Settings.CfClient.DescribeStacksAsync(new DescribeStacksRequest {
                StackName = stackId
            });

            return(Stack : description.Stacks.FirstOrDefault(), Success : success);
        }
示例#14
0
        public static async Task <(Stack Stack, bool Success)> TrackStackUpdateAsync(
            this IAmazonCloudFormation cfnClient,
            string stackName,
            string stackId,
            string mostRecentStackEventId,
            ModuleNameMappings nameMappings = null,
            LogErrorDelegate logError       = null
            )
        {
            var seenEventIds = new HashSet <string>();
            var foundMostRecentStackEvent = (mostRecentStackEventId == null);
            var request = new DescribeStackEventsRequest {
                StackName = stackId ?? stackName
            };
            var eventList        = new List <StackEvent>();
            var ansiLinesPrinted = 0;

            // iterate as long as the stack is being created/updated
            var active  = true;
            var success = false;

            while (active)
            {
                await Task.Delay(TimeSpan.FromSeconds(3));

                // fetch as many events as possible for the current stack
                var events = new List <StackEvent>();
                try {
                    var response = await cfnClient.DescribeStackEventsAsync(request);

                    events.AddRange(response.StackEvents);
                } catch (System.Net.Http.HttpRequestException e) when((e.InnerException is System.Net.Sockets.SocketException) && (e.InnerException.Message == "No such host is known"))
                {
                    // ignore network issues and just try again
                    continue;
                }
                events.Reverse();

                // skip any events that preceded the most recent event before the stack update operation
                while (!foundMostRecentStackEvent && events.Any())
                {
                    var evt = events.First();
                    if (evt.EventId == mostRecentStackEventId)
                    {
                        foundMostRecentStackEvent = true;
                    }
                    seenEventIds.Add(evt.EventId);
                    events.RemoveAt(0);
                }
                if (!foundMostRecentStackEvent)
                {
                    throw new ApplicationException($"unable to find starting event for stack: {stackName}");
                }

                // report only on new events
                foreach (var evt in events.Where(evt => !seenEventIds.Contains(evt.EventId)))
                {
                    UpdateEvent(evt);
                    if (!seenEventIds.Add(evt.EventId))
                    {
                        // we found an event we already saw in the past, no point in looking at more events
                        break;
                    }
                    if (IsFinalStackEvent(evt) && (evt.LogicalResourceId == stackName))
                    {
                        // event signals stack creation/update completion; time to stop
                        active  = false;
                        success = IsSuccessfulFinalStackEvent(evt);
                        break;
                    }
                }
                RenderEvents();
            }
            if (!success)
            {
                return(Stack : null, Success : false);
            }

            // describe stack and report any output values
            var description = await cfnClient.DescribeStacksAsync(new DescribeStacksRequest {
                StackName = stackName
            });

            return(Stack : description.Stacks.FirstOrDefault(), Success : success);

            // local function
            string TranslateLogicalIdToFullName(string logicalId)
            {
                var fullName = logicalId;

                nameMappings?.ResourceNameMappings?.TryGetValue(logicalId, out fullName);
                return(fullName ?? logicalId);
            }

            string TranslateResourceTypeToFullName(string awsType)
            {
                var fullName = awsType;

                nameMappings?.TypeNameMappings?.TryGetValue(awsType, out fullName);
                return(fullName ?? awsType);
            }

            void RenderEvents()
            {
                if (Settings.UseAnsiConsole)
                {
                    if (ansiLinesPrinted > 0)
                    {
                        Console.Write(AnsiTerminal.MoveLineUp(ansiLinesPrinted));
                    }
                    var maxResourceStatusLength   = eventList.Any() ? eventList.Max(evt => evt.ResourceStatus.ToString().Length) : 0;
                    var maxResourceTypeNameLength = eventList.Any() ? eventList.Max(evt => TranslateResourceTypeToFullName(evt.ResourceType).Length) : 0;
                    foreach (var evt in eventList)
                    {
                        var resourceStatus = evt.ResourceStatus.ToString();
                        var resourceType   = TranslateResourceTypeToFullName(evt.ResourceType);
                        if (_ansiStatusColorCodes.TryGetValue(evt.ResourceStatus, out var ansiColor))
                        {
                            // print resource status
                            Console.Write(ansiColor);
                            Console.Write(resourceStatus);
                            Console.Write(AnsiTerminal.Reset);
                            Console.Write("".PadRight(maxResourceStatusLength - resourceStatus.Length + 4));

                            // print resource type
                            Console.Write(resourceType);
                            Console.Write("".PadRight(maxResourceTypeNameLength - resourceType.Length + 4));

                            // print resource name
                            Console.Write(TranslateLogicalIdToFullName(evt.LogicalResourceId));

                            // print status reason
                            if ((logError == null) && (evt.ResourceStatusReason != null))
                            {
                                Console.Write($" ({evt.ResourceStatusReason})");
                            }
                        }
                        else
                        {
                            Console.Write($"{resourceStatus}    {resourceType}    {TranslateLogicalIdToFullName(evt.LogicalResourceId)}{(evt.ResourceStatusReason != null ? $" ({evt.ResourceStatusReason})" : "")}");
                        }
                        Console.Write(AnsiTerminal.ClearEndOfLine);
                        Console.WriteLine();
                    }
                    ansiLinesPrinted = eventList.Count;
                }
            }

            void UpdateEvent(StackEvent evt)
            {
                if (Settings.UseAnsiConsole)
                {
                    var index = eventList.FindIndex(e => e.LogicalResourceId == evt.LogicalResourceId);
                    if (index < 0)
                    {
                        eventList.Add(evt);
                    }
                    else
                    {
                        eventList[index] = evt;
                    }
                }
                else
                {
                    Console.WriteLine($"{evt.ResourceStatus,-35} {TranslateResourceTypeToFullName(evt.ResourceType),-55} {TranslateLogicalIdToFullName(evt.LogicalResourceId)}{(evt.ResourceStatusReason != null ? $" ({evt.ResourceStatusReason})" : "")}");
                }

                // capture failed operation as an error
                switch (evt.ResourceStatus)
                {
                case "CREATE_FAILED":
                case "ROLLBACK_FAILED":
                case "UPDATE_FAILED":
                case "DELETE_FAILED":
                case "UPDATE_ROLLBACK_FAILED":
                case "UPDATE_ROLLBACK_IN_PROGRESS":
                    if (evt.ResourceStatusReason != "Resource creation cancelled")
                    {
                        logError?.Invoke($"{evt.ResourceStatus} {TranslateLogicalIdToFullName(evt.LogicalResourceId)} [{TranslateResourceTypeToFullName(evt.ResourceType)}]: {evt.ResourceStatusReason}", /*Exception*/ null);
                    }
                    break;
                }
            }
        }
示例#15
0
 /// <summary>
 ///  查询资源栈事件列表
 /// </summary>
 /// <param name="request">请求参数信息</param>
 /// <returns>请求结果信息</returns>
 public async Task <DescribeStackEventsResponse> DescribeStackEvents(DescribeStackEventsRequest request)
 {
     return(await new DescribeStackEventsExecutor().Client(this).Execute <DescribeStackEventsResponse, DescribeStackEventsResult, DescribeStackEventsRequest>(request).ConfigureAwait(false));
 }
示例#16
0
 /// <summary>
 ///  查询资源栈事件列表
 /// </summary>
 /// <param name="request">请求参数信息</param>
 /// <returns>请求结果信息</returns>
 public DescribeStackEventsResponse DescribeStackEvents(DescribeStackEventsRequest request)
 {
     return(new DescribeStackEventsExecutor().Client(this).Execute <DescribeStackEventsResponse, DescribeStackEventsResult, DescribeStackEventsRequest>(request));
 }