Example #1
0
        private bool CommandsTooFast(ChatMessageEventArgs chatMessageArgs, ChatUserInfo user, string namedCommand, TimeSpan?cooldown = null)
        {
            Debug.Assert(user != null);

            if (chatMessageArgs.IsModerator || chatMessageArgs.IsOwner)
            {
                return(false);
            }

            var now = DateTime.UtcNow;

            if (now - user.LastCommandTime < CooldownTime)
            {
                _logger?.LogWarning($"Ignoring command {namedCommand} from {chatMessageArgs.UserName} on {chatMessageArgs.ServiceName}. Cooldown active");

                return(true);
            }

            if (_commandExecutedTimeMap.TryGetValue(namedCommand, out var dt)
                &&
                now - dt < cooldown.GetValueOrDefault())
            {
                var remain = cooldown.GetValueOrDefault() - (now - dt);
                _logger?.LogWarning($"Ignoring command {namedCommand} from {chatMessageArgs.UserName} on {chatMessageArgs.ServiceName}. In cooldown for {(int)remain.TotalSeconds} more secs");

                return(true);
            }

            return(false);
        }
Example #2
0
        private void AfterExecute(ChatUserInfo user, string command)
        {
            Debug.Assert(user != null);

            // Remember last command time
            user.LastCommandTime             = DateTime.UtcNow;
            _commandExecutedTimeMap[command] = DateTime.UtcNow;
        }
Example #3
0
        private async ValueTask <bool> HandleExtendedCommands(IChatService chatService, ChatMessageEventArgs chatMessageArgs, ChatUserInfo user)
        {
            Debug.Assert(_extendedCommands != null);

            foreach (var cmd in _extendedCommands)
            {
                Debug.Assert(!string.IsNullOrEmpty(cmd.Name));

                if (cmd.CanExecute(chatMessageArgs.UserName, chatMessageArgs.Message))
                {
                    // Ignore if the normal user is sending commands to fast, or command is in cooldown
                    if (CommandsTooFast(chatMessageArgs, user, cmd.Name, cmd.Cooldown))
                    {
                        return(false);
                    }

                    await cmd.Execute(chatService, chatMessageArgs.UserName, chatMessageArgs.Message);

                    AfterExecute(user, cmd.Name);

                    return(cmd.Final);
                }
            }

            return(false);
        }
Example #4
0
        private async ValueTask <bool> HandleBasicCommands(IChatService chatService, ChatMessageEventArgs chatMessageArgs, ChatUserInfo user)
        {
            Debug.Assert(_basicCommands != null);
            Debug.Assert(!string.IsNullOrEmpty(chatMessageArgs.Message) && chatMessageArgs.Message[0] == '!');

            var trigger = chatMessageArgs.Message.AsMemory(1);
            var rhs     = ReadOnlyMemory <char> .Empty;
            var n       = trigger.Span.IndexOf(' ');

            if (n != -1)
            {
                rhs     = trigger.Slice(n + 1);
                trigger = trigger.Slice(0, n);
            }

            foreach (var cmd in _basicCommands)
            {
                Debug.Assert(!string.IsNullOrEmpty(cmd.Trigger));

                if (trigger.Span.Equals(cmd.Trigger.AsSpan(), StringComparison.OrdinalIgnoreCase))
                {
                    // Ignore if the normal user is sending commands to fast, or command is in cooldown
                    if (CommandsTooFast(chatMessageArgs, user, cmd.Trigger, cmd.Cooldown))
                    {
                        return(true);
                    }

                    if (cmd is IBasicCommand2)
                    {
                        await(cmd as IBasicCommand2).Execute(chatService, chatMessageArgs.UserName, chatMessageArgs.IsModerator, chatMessageArgs.IsOwner, rhs);
                    }
                    else
                    {
                        await cmd.Execute(chatService, chatMessageArgs.UserName, rhs);
                    }

                    AfterExecute(user, cmd.Trigger);

                    return(true);
                }
            }

            return(false);
        }