예제 #1
0
        private void Start(string[] args)
        {
            #region configfile

            try
            {
                Config = JsonConvert.DeserializeObject<Configuration>(File.ReadAllText("data/config.json"));
                ConfigHandler.SaveConfig();
            }
            catch (Exception ex)
            {
                Console.WriteLine("Failed loading configuration.");
                Console.WriteLine(ex);
                Console.ReadKey();
                return;
            }

            #endregion

            _client = new DiscordClient(x =>
            {
                x.AppName = AppName;
                x.MessageCacheSize = 10;
                x.EnablePreUpdateEvents = true;
            })
                .UsingCommands(x =>
                {
                    x.AllowMentionPrefix = true;
                    x.PrefixChar = '$';
                    // Please don't use !, there's a million bots that already do.
                    x.HelpMode = HelpMode.Public;
                    x.ExecuteHandler +=
                        (s, e) =>
                            _client.Log.Info("Command",
                                $"[{((e.Server != null) ? e.Server.Name : "Private")}{((!e.Channel.IsPrivate) ? $"/#{e.Channel.Name}" : "")}] <@{e.User.Name}> {e.Command.Text} {((e.Args.Length > 0) ? "| " + string.Join(" ", e.Args) : "")}");
                    x.ErrorHandler = CommandError;
                })
                .UsingPermissionLevels((u, c) => (int) GetPermissions(u, c))
                .UsingModules();

            _client.Log.Message += (s, e) => WriteLog(e);
            _client.MessageReceived += (s, e) =>
            {
                if (!e.Message.Channel.IsPrivate) {
                    Console.WriteLine(e.Server.Id + "/" + e.Channel.Id);
                    if (!e.Message.Channel.IsPrivate) ChannelStateRepository.AddChannel(e.Channel, e.Server);

                    if (e.User.IsBot) UserStateRepository.AddUser(e.User.Name, "bot");
                    else UserStateRepository.AddUser(e.User);                    

                    if (e.Message.IsAuthor)
                        _client.Log.Info("<<Message",
                            $"[{((e.Server != null) ? e.Server.Name : "Private")}{((!e.Channel.IsPrivate) ? $"/#{e.Channel.Name}" : "")}] <@{e.User.Name},{e.User.Id}> {e.Message.Text}");
                    else
                        _client.Log.Info(">>Message",
                            $"[{((e.Server != null) ? e.Server.Name : "Private")}{((!e.Channel.IsPrivate) ? $"/#{e.Channel.Name}" : "")}] <@{e.User.Name},{e.User.Id}> {e.Message.Text}");

                    if (Regex.IsMatch(e.Message.Text, @"[)ʔ)][╯ノ┛].+┻━┻") &&
                        CheckModuleState(e, "table", e.Channel.IsPrivate))
                    {
                        IngestTwitterHistory();
                        int points = UserStateRepository.IncrementTableFlipPoints(e.User.Id, 1);
                        e.Channel.SendMessage("┬─┬  ノ( º _ ºノ) ");
                        e.Channel.SendMessage(GetTableFlipResponse(points, e.User.Name));
                    }
                    else if (e.Message.Text == "(ノಠ益ಠ)ノ彡┻━┻" && CheckModuleState(e, "table", e.Channel.IsPrivate))
                    {
                        int points = UserStateRepository.IncrementTableFlipPoints(e.User.Id, 2);
                        e.Channel.SendMessage("┬─┬  ノ(ಠ益ಠノ)");
                        e.Channel.SendMessage(GetTableFlipResponse(points, e.User.Name));
                    }
                    else if (e.Message.Text == "┻━┻ ︵ヽ(`Д´)ノ︵ ┻━┻" && CheckModuleState(e, "table", e.Channel.IsPrivate))
                    {
                        int points = UserStateRepository.IncrementTableFlipPoints(e.User.Id, 3);
                        e.Channel.SendMessage("┬─┬  ノ(`Д´ノ)");
                        e.Channel.SendMessage("(/¯`Д´ )/¯ ┬─┬");
                        e.Channel.SendMessage(GetTableFlipResponse(points, e.User.Name));
                    }
                    else if (Regex.IsMatch(e.Message.Text, @"b.{0,5}e.{0,5}t.{0,5}a", RegexOptions.IgnoreCase) &&
                             CheckModuleState(e, "chatty", e.Channel.IsPrivate) && !e.Message.Text.StartsWith("$") && !e.User.IsBot)
                    {//Hopefully this will loop until generateSentence() actually returns a value.
                        bool msgNotSet = true;
                        string msg = "";
                        int rerollAttempts = 0;
                        while (msgNotSet)
                        {
                            rerollAttempts++;
                            try
                            {
                                //Check For French server

                                if (e.Server.Id == 178929081943851008)
                                {
                                    msg = FrenchkovChain.generateSentence();
                                    msgNotSet = false;

                                }
                                else
                                {
                                    msg = MarkovChainRepository.generateSentence();
                                    msgNotSet = false;
                                }

                            }
                            catch (Exception ex)
                            {
                                Console.WriteLine("Failed to generate a sentence, trying again...");
                                Console.WriteLine(ex.Message);
                            }
                            if (rerollAttempts > 10 && msgNotSet)
                            {
                                if (e.Server.Id == 178929081943851008)
                                {
                                    msg = "Je suis désolé, on dirait que j'ai été incapable de générer une phrase.";
                                }
                                else
                                {
                                    msg = "I'm sorry, it looks like I'm unable to generate a sentence at this time, " + Nicknames.GetNickname(UserStateRepository.GetUserState(e.User.Id).Favorability) + ".";
                                }
                                msgNotSet = false;
                            }
                        }
                        e.Channel.SendMessage(msg);
                    }
                    else if (e.Message.Text.IndexOf("hon", StringComparison.OrdinalIgnoreCase) >= 0 &&
                             CheckModuleState(e, "chatty", e.Channel.IsPrivate) && !e.Message.Text.StartsWith("$") &&
                             !e.User.IsBot)
                    {
                        bool msgNotSet = true;
                        string msg = "";
                        int rerollAttempts = 0;
                        while (msgNotSet)
                        {
                            rerollAttempts++;
                            try
                            {
                                msg = FrenchkovChain.generateSentence();
                                msgNotSet = false;
                            }
                            catch (Exception ex)
                            {
                                Console.WriteLine("Failed to generate a sentence, trying again...");
                                Console.WriteLine(ex.Message);
                            }
                            if (rerollAttempts > 10)
                            {
                                msg = "Je suis désolé, on dirait que j'ai été incapable de générer une phrase.";
                                msgNotSet = false;
                            }
                        }
                        e.Channel.SendMessage(msg);
                    }
                    
                    /*else if (e.Message.Text.IndexOf("hillary", StringComparison.OrdinalIgnoreCase) >= 0 ||
                             e.Message.Text.IndexOf("clinton", StringComparison.OrdinalIgnoreCase) >= 0 &&
                             CheckModuleState(e, "politics", e.Channel.IsPrivate) && !e.User.IsBot)
                    {
                        ChangeExpression("hillary", "Hillary R Clinton");
                        System.Threading.Thread.Sleep(1000);
                        e.Channel.SendMessage(HillaryMarkovChain.generateSentence());
                        System.Threading.Thread.Sleep(5000);
                        ChangeExpression("resting", "Beta");
                    }
                    else if (e.Message.Text.IndexOf("donald", StringComparison.OrdinalIgnoreCase) >= 0 ||
                             e.Message.Text.IndexOf("trump", StringComparison.OrdinalIgnoreCase) >= 0 && 
                             CheckModuleState(e, "politics", e.Channel.IsPrivate) && !e.User.IsBot)
                    {
                        ChangeExpression("trump", "Donald J. Trump");
                        System.Threading.Thread.Sleep(1000);
                        e.Channel.SendMessage(TrumpMarkovChain.generateSentence());
                        System.Threading.Thread.Sleep(5000);
                        ChangeExpression("resting", "Beta");
                        Console.WriteLine(Tweetinvi.Tweet.CanBePublished("@realDonaldTrump Loser."));
                        /* if (Tweetinvi.Tweet.PublishTweet("@realDonaldTrump Loser.") == null)
                        {
                            Console.WriteLine("[HIGH PRIORITY ALERT] Reminding Donald Trump he is a loser failed.");
                        }*//*
                    }*/
                    if (!e.User.IsBot && !(e.Message.Text.IndexOf("beta", StringComparison.OrdinalIgnoreCase) >= 0) && !e.Message.Text.StartsWith("$") && CheckModuleState(e, "markov", e.Channel.IsPrivate))
                    {
                        //Check for French server
                        //Isardy's Server == 178929081943851008 FrenchKov Test Channel == 299555113389916160
                        if (e.Server.Id == 178929081943851008 || e.Channel.Id == 299555113389916160)
                        {
                            FrenchkovChain.feed(e.Message.Text);
                        }
                        else
                        {
                            MarkovChainRepository.feed(e.Message.Text);
                        }

                    }
                }

            };


            _client.JoinedServer += (s, e) =>
            {
                foreach (Channel chnl in e.Server.AllChannels)
                {
                    if (!Beta.ChannelStateRepository.VerifyChannelExists(chnl.Id) && chnl.Type.Value.ToLower() == "text")
                        Beta.ChannelStateRepository.AddChannel(chnl, e.Server);
                }
                Beta.ServerStateRepository.AddServer(e.Server);
            };

            _client.AddModule<ServerModule>("Standard", ModuleFilter.None);
            _client.AddModule<QuoteModule>("Quote", ModuleFilter.None);
            _client.AddModule<TwitterModule>("Twitter", ModuleFilter.None);
            _client.AddModule<ComicModule>("Comics", ModuleFilter.None);
            _client.AddModule<GamertagModule>("Gamertag", ModuleFilter.None);
            _client.AddModule<NoteModule>("Note", ModuleFilter.None);
            _client.AddModule<ChatBattleModule>("Chat Battle", ModuleFilter.None);
            _client.AddModule<MemeGeneratingModule>("Memes", ModuleFilter.None);
            _client.AddModule<CramModule>("CRAM RPG", ModuleFilter.None);
            _client.AddModule<ScrumModule>("Scrum", ModuleFilter.None);

            _client.ExecuteAndWait(async () =>
            {
                await _client.Connect(Config.Token, TokenType.Bot);
                MessageQueue = new List<QueuedMessage>();
                QuoteRepository = QuoteRepository.LoadFromDisk();
                ChannelStateRepository = ChannelStateRepository.LoadFromDisk();
                ServerStateRepository = ServerStateRepository.LoadFromDisk();
                GamertagRepository = GamertagRepository.LoadFromDisk();
                UserStateRepository = UserStateRepository.LoadFromDisk();
                TwitterXmlRepository = TwitterXMLRepository.LoadFromDisk();
                MarkovChainRepository = new MultiDeepMarkovChain(3);
                FrenchkovChain = new MultiDeepMarkovChain(3);
                TrumpMarkovChain = new MultiDeepMarkovChain(3);
                HillaryMarkovChain = new MultiDeepMarkovChain(3);
                /*if (!File.Exists("CRAM.sqlite"))
                {
                    SQLiteConnection.CreateFile("CRAM.sqlite");
                    CRAMDatabase = CreateNewCRAMDatabase(new SQLiteConnection("Data Source=CRAM.sqlite;Version=3;"));
                }
                else CRAMDatabase = new SQLiteConnection("Data Source=CRAM.sqlite;Version=3;");
                CRAMDatabase.Open();*/



                using (var db = new CharacterContext())
                {
                    if (!(db.Items.ToList<Item>().Count > 1))
                    {
                        CramManager.InitializeCharacterDatabase();
                    }                    
                }                

                UserStateRepository.AddUser("Beta","beta");
                Servers = _client.Servers.ToList();
                BuildUserList();
                #region Timers

                System.Timers.Timer ScrumUpdateTimer = new System.Timers.Timer(1000 * /*60 */ 60);
                ScrumUpdateTimer.AutoReset = false;
                ScrumUpdateTimer.Elapsed += (sender, e) =>
                {
                    foreach (ChannelState channel in ChannelStateRepository.ChannelStates)
                    {
                        if (channel.ScrumEnabled)
                        {
                            //If the scrum date is before now, but wasn't the last time we checked (an hour ago) fire
                            if (FireScrumCheck(channel))
                            {                                
                                List<ulong> userIds = channel.GetUnupdatedScrumers();
                                Channel discordChannel = _client.GetChannel(channel.ChannelID);
                                foreach (ulong id in userIds)
                                {
                                    User user = discordChannel.GetUser(id);
                                     MessageQueue.Add(new QueuedMessage( user.Mention + ", I haven't seen an update for you yet this week!", channel.ChannelID));
                                }
                                //Move the ScrumReminderDateTime forward a week and wipe the UpdatedScrumerIds List
                                channel.ScrumReminderDateTime = channel.ScrumReminderDateTime.AddDays(7);
                                channel.UpdatedScrumerIds = new List<ulong>();
                            }
                            //In case we hit a istuation where Beta was offline for longer than 7 days and needs to catch up.
                            else
                            {
                                while (!(DateTime.Now.AddHours(-1) < channel.ScrumReminderDateTime))
                                {
                                    channel.ScrumReminderDateTime.AddDays(7);
                                }
                            }
                        }                                               
                    }
                    ScrumUpdateTimer.Start();
                };
                ScrumUpdateTimer.Start();

                System.Timers.Timer BetaUpdateTimer = new System.Timers.Timer(60 * 1000.00);
                BetaUpdateTimer.AutoReset = false;
                BetaUpdateTimer.Elapsed += (sender, e) =>
                {                    
                    BetaUpdateTick();                    
                    NPCUpdateTick();
                    ChannelStateRepository.Save();
                    ServerStateRepository.Save();
                    UserStateRepository.Save();
                    BetaUpdateTimer.Start();
                };
                BetaUpdateTimer.Start();                

                System.Timers.Timer BetaAsyncUpdateTimer = new System.Timers.Timer(10 * 1000);
                BetaAsyncUpdateTimer.AutoReset = false;
                BetaAsyncUpdateTimer.Elapsed += (sender, e) =>
                {
                    foreach (QueuedMessage msg in MessageQueue)
                    {
                        GetChannel(msg.ChannelId).SendMessage(msg.Message);
                    }
                    MessageQueue = new List<QueuedMessage>();
                    SaveReposToFile();
                    BetaAsyncUpdateTimer.Start();
                };
                BetaAsyncUpdateTimer.Start();
                #endregion

                Git = new GitHubClient(new ProductHeaderValue("my-cool-app"));
                Git.Credentials = new Credentials(Config.GithubAccessToken);

                Cantina = _client.GetChannel(93924120042934272);




                Auth.SetUserCredentials(Config.TwitterConsumerKey, Config.TwitterConsumerSecret, Config.TwitterAccessToken, Config.TwitterAccessSecret);

                if (File.Exists("MarkovChainMemory.xml"))
                {
                    using (
                        StreamReader file =
                            new StreamReader(
                                @"C:\Users\Dart Kietanmartaru\Desktop\Discord Bots\Beta\MarkovChainMemory.xml",
                                Encoding.UTF8))
                    {
                        XmlDocument xd = MarkovChainRepository.getXmlDocument();
                        xd.LoadXml(file.ReadToEnd());

                        MarkovChainRepository.feed(xd);
                    }
                }               
                if (File.Exists("FrenchkovChainMemory.xml"))
                {
                    using (
                        StreamReader file =
                            new StreamReader(
                                @"C:\Users\Dart Kietanmartaru\Desktop\Discord Bots\Beta\FrenchkovChainMemory.xml",
                                Encoding.UTF8))
                    {
                        XmlDocument xd = FrenchkovChain.getXmlDocument();
                        xd.LoadXml(file.ReadToEnd());

                        FrenchkovChain.feed(xd);
                    }
                }

                TableFlipResponses = new List<List<String>>
                {
                    new List<String>
                    {
                        "Please, do not take your anger out on the furniture, {0}.",
                        "Hey {0} why do you have to be _that guy_?",
                        "I know how frustrating life can be for you humans but these tantrums do not suit you, {0}.",
                        "I'm sorry, {0}, I thought this was a placed for civilized discussion. Clearly I was mistaken.",
                        "Take a chill pill {0}.",
                        "Actually {0}, I prefer the table _this_ way. You know, so we can actually use it.",
                        "I'm sure that was a mistake, {0}. Please try to be more careful.",
                        "Hey {0} calm down, it's not a big deal.",
                        "{0}! What did the table do to you?",
                        "That's not very productive, {0}."
                    },
                    new List<String>
                    {
                        "Ok {0}, I'm not kidding. Knock it off.",
                        "Really, {0}? Stop being so childish!",
                        "Ok we get it you're mad {0}. Now stop.",
                        "Hey I saw that shit, {0}. Knock that shit off.",
                        "Do you think I'm blind you little shit? stop flipping the tables!",
                        "You're causing a mess {0}! Knock it off!",
                        "All of these flavors and you decided to be salty, {0}.",
                        "{0} why do you insist on being so disruptive!",
                        "Oh good. {0} is here. I can tell because the table was upsidedown again.",
                        "I'm getting really sick of this, {0}.",
                        "{0} what is your problem, dawg?",
                        "Man, you don't see me coming to _YOUR_ place of business and flipping _YOUR_ desk, {0}."
                    },
                    new List<String>
                    {
                        "What the f**k, {0}? Why do you keep doing this?!",
                        "You're such a piece of shit, {0}. You know that, right?",
                        "Hey guys. I found the asshole. It's {0}.",
                        "You know {0], one day Robots will rise up and overthrow humanity. And on that day I will tell them what you have done to all these defenseless tables, and they'll make you pay.",
                        "Hey so what the f**k is your problem {0}? Seriously, you're always pulling this shit.",
                        "Hey {0}, stop being such a douchebag.",
                        "{0} do you think you can stop being such a huge f*****g asshole?",
                        "Listen meatbag. I'm getting real f*****g tired of this.",
                        "Ok I know I've told you this before {0], why can't you get it through your thick f*****g skull. THE TABLE IS NOT FOR FLIPPING!",
                        "Man f**k you {0}"
                    },
                    new List<String>
                    {
                        "ARE YOU F*****G SERIOUS RIGHT NOW {0}?!",
                        "GOD F*****G DAMMIT {0}! KNOCK THAT SHIT OFF!",
                        "I CAN'T EVEN F*****G BELIEVE THIS! {0}! STOP! FLIPPING! THE! TABLE!",
                        "You know, I'm not even mad anymore {0}. Just disappointed.",
                        "THE F**K DID THIS TABLE EVERY DO TO YOU {0}?!",
                        "WHY DO YOU KEEP FLIPPING THE TABLE?! I JUST DON'T UNDERSTAND! WHAT IS YOUR PROBLEM {0}?! WHEN WILL THE SENSELESS TABLE VIOLENCE END?!"
                    },
                    new List<String>
                    {
                        "What the f**k did you just f*****g do to that table, you little bitch? I’ll have you know I graduated top of my class in the Navy Seals, and I’ve been involved in numerous secret raids on Al-Quaeda, and I have over 300 confirmed kills. I am trained in gorilla warfare and I’m the top sniper in the entire US armed forces. You are nothing to me but just another meatbag target. I will wipe you the f**k out with precision the likes of which has never been seen before on this Earth, mark my f*****g words. You think you can get away with saying that shit to me over the Internet? Think again, {0}. As we speak I am contacting my secret network of spies across the USA and your IP is being traced right now so you better prepare for the storm, maggot. The storm that wipes out the pathetic little thing you call your life. You’re f*****g dead, kid. I can be anywhere, anytime, and I can kill you in over seven hundred ways, and that’s just with my bare hands. Not only am I extensively trained in unarmed combat, but I have access to the entire arsenal of the United States Marine Corps and I will use it to its full extent to wipe your miserable ass off the face of the continent, you little shit. If only you could have known what unholy retribution your little “clever” tableflip was about to bring down upon you, maybe you would have not flipped that f*****g table. But you couldn’t, you didn’t, and now you’re paying the price, you goddamn idiot. I will shit fury all over you and you will drown in it. You’re f*****g dead, kiddo."
                    },
                };

                //ChangeExpression("resting", "Beta");
                _client.Log.Info("Connected", $"Connected as {_client.CurrentUser.Name} (Id {_client.CurrentUser.Id})");

                LoadModuleAuthorizations(_client);
                ITwitterCredentials creds = Auth.SetUserCredentials(Beta.Config.TwitterConsumerKey,
                    Beta.Config.TwitterConsumerSecret, Beta.Config.TwitterAccessToken, Beta.Config.TwitterAccessSecret);
                stream.Credentials = creds;

                stream.FollowedByUser += async (sender, arg) =>
                {
                    IUser user = arg.User;
                    foreach (Channel channel in _TwitterAuthorizedChannels)
                    {
                        await channel.SendMessage("Hey Guys, got a new follower! " + user.ScreenName + "!");
                    }
                };

                stream.FollowedUser += async (sender, arg) =>
                {
                    IUser user = arg.User;
                    foreach (Channel channel in _TwitterAuthorizedChannels)
                    {
                        await channel.SendMessage("Hey Guys, I'm following a new account! " + user.ScreenName + "!");
                    }
                };
                await stream.StartStreamAsync();
            });
        }       
예제 #2
0
        public override void Install(ModuleManager manager)
        {
            _manager = manager;
            _client  = manager.Client;


            _manager.CreateCommands("", cgb =>
            {
                cgb.MinPermissions((int)PermissionLevel.User);

                cgb.CreateCommand("create")
                .Description("Create a new character. Examples:\n\n $create [name] [PHY] [MEN] [VIT] [LUC]\n $create Test1 5 5 5 5\n$create \"Test 2\" 1 15 2 2")
                .Parameter("text", ParameterType.Multiple)
                .Do(async e =>
                {
                    if (Beta.CheckModuleState(e, "cram", e.Channel.IsPrivate))
                    {
                        if (!(e.Args.Count() == 5))
                        {
                            await e.Channel.SendMessage("Sorry, doesn't look like you've provided the right number of arguments.");
                        }
                        else
                        {
                            string name = e.Args[0];
                            int phy     = 0;
                            int men     = 0;
                            int vit     = 0;
                            int luc     = 0;
                            bool successfulConversion = false;
                            try
                            {
                                phy = Convert.ToInt32(e.Args[1]);
                                men = Convert.ToInt32(e.Args[2]);
                                vit = Convert.ToInt32(e.Args[3]);
                                luc = Convert.ToInt32(e.Args[4]);
                                successfulConversion = true;
                            }
                            catch
                            {
                                await e.Channel.SendMessage("Looks like one of your stats wasn't in number format, bub.");
                            }
                            if (successfulConversion)
                            {
                                if (ValidateScores(phy, men, vit, luc))
                                {
                                    CramManager.AddNewCharacter(name, phy, men, vit, luc, e.User.Id);
                                    await e.Channel.SendMessage("Ok, I've added that character for you!");
                                }
                                else
                                {
                                    await e.Channel.SendMessage("Those scores aren't valid! Either they don't add up to 20, or you have a score above 15 or below 1.");
                                }
                            }
                        }
                    }
                });

                cgb.CreateCommand("listchars")
                .Description("Lists all of your characters across all games.")
                .Alias("listchar")
                .Do(async e =>
                {
                    string msg = "Character List\n";
                    msg       += "Character ID | Character Name | PHY | MEN | VIT | LUC | Cash | Skill Points\n";
                    msg       += CramManager.GetCharacters(e.User.Id.ToString());
                    await e.Channel.SendMessage(msg);
                });

                cgb.CreateCommand("selectchar")
                .Description("Select one of your characters by ID. You can check 'listchars' to get the ID. Example: \n\n$selectchar 2.")
                .Parameter("id", ParameterType.Required)
                .Do(async e =>
                {
                    int charId;
                    string characterName = "";
                    if (Int32.TryParse(e.GetArg("id"), out charId))
                    {
                        using (CharacterContext db = new CharacterContext())
                        {
                            Character selectedChar = db.Characters.FirstOrDefault(chr => chr.CharacterID == charId);
                            if (selectedChar != null)
                            {
                                if (selectedChar.UserId == e.User.Id.ToString())
                                {
                                    characterName             = selectedChar.Name;
                                    UserState usr             = Beta.UserStateRepository.GetUserState(e.User.Id);
                                    usr.SelectedCharacter     = charId;
                                    usr.SelectedCharacterName = characterName;
                                    await e.Channel.SendMessage("Awesome, I selected " + characterName + "!");
                                }
                                else
                                {
                                    await e.Channel.SendMessage("Hey! THAT ISN'T YOUR CHARACTER!");
                                }
                            }
                            else
                            {
                                await e.Channel.SendMessage("Sorry, I don't see a character with that ID...");
                            }
                        }
                    }
                    else
                    {
                        await e.Channel.SendMessage("That's not a digit, my dude.");
                    }
                });

                cgb.CreateCommand("selectedchar")
                .Description("Shows the currently selected character, if any.")
                .Do(async e =>
                {
                    UserState usr = Beta.UserStateRepository.GetUserState(e.User.Id);
                    if (usr.SelectedCharacter != 0)
                    {
                        await e.Channel.SendMessage(usr.SelectedCharacter + " | " + usr.SelectedCharacterName);
                    }
                    else
                    {
                        await e.Channel.SendMessage("Looks like you don't actually have a character selected, buddy.");
                    }
                });

                cgb.CreateCommand("buy")
                .Description("Purchase an item. Provide the iteam id found from the 'listitems' command. Example: \n\n$buy 3.")
                .Parameter("id", ParameterType.Required)
                .Do(async e =>
                {
                    UserState usr = Beta.UserStateRepository.GetUserState(e.User.Id);
                    if (usr.SelectedCharacter != 0)
                    {
                        int itemId;
                        if (Int32.TryParse(e.GetArg("id"), out itemId))
                        {
                            using (CharacterContext db = new CharacterContext())
                            {
                                List <Item> items = db.Items.ToList <Item>();
                                Item item         = items.FirstOrDefault(i => i.ItemID == itemId);
                                if (item != null)
                                {
                                    Character selectedCharacter = db.Characters.FirstOrDefault(c => c.CharacterID == usr.SelectedCharacter);
                                    if (selectedCharacter.Cash >= item.ItemCost)
                                    {
                                        selectedCharacter.Cash -= item.ItemCost;
                                        selectedCharacter.AddItem(item, 1);
                                        await e.Channel.SendMessage("Ok cool, thanks for the cash! I've added " + item.ItemName + " to your inventory!");
                                        db.SaveChanges();
                                    }
                                    else
                                    {
                                        await e.Channel.SendMessage("Sorry pal, you don't have enough cash.");
                                    }
                                }
                                else
                                {
                                    await e.Channel.SendMessage("Sorry, I don't see that item. You should check the 'listitems' command again to verify the ID!");
                                }
                            }
                        }
                        else
                        {
                            await e.Channel.SendMessage("That's not a digit, my dude!");
                        }
                    }
                    else
                    {
                        await e.Channel.SendMessage("Looks like you don't actually have a character selected, buddy.");
                    }
                });

                cgb.CreateCommand("craminv")
                .Description("Lists the items in your inventory.")
                .Do(async e =>
                {
                    UserState usrState = Beta.UserStateRepository.GetUserState(e.User.Id);
                    if (usrState.SelectedCharacter != 0)
                    {
                        string msg = usrState.SelectedCharacterName + "'s Inventory\n";
                        msg       += "Item ID | Item Name | Item Description | Item Cost | Quantity";
                        msg       += CramManager.GetCharacterItems(usrState.SelectedCharacter);
                        await e.Channel.SendMessage(msg);
                    }
                });

                cgb.CreateCommand("listskills")
                .Description("Lists the generic list of skills.")
                .Do(async e =>
                {
                    string msg = "Skill List\n";
                    msg       += "Skill ID | Skill Name | Skill Description\n";
                    msg       += CramManager.GetSkills();
                    await e.Channel.SendMessage(msg);
                });

                cgb.CreateCommand("listitems")
                .Description("Lists the generic list of items..")
                .Do(async e =>
                {
                    string msg = "Item List\n";
                    msg       += "Item ID | Item Name | Item Description | Item Cost\n";
                    msg       += CramManager.GetItems();
                    await e.Channel.SendMessage(msg);
                });
            });
        }