{"action":"created","comment":{"url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/comments/90156741","pull_request_review_id":10680043,"id":90156741,"diff_hunk":"@@ -2,71 +2,197 @@ const conf = require('../conf/config.json');\n const fs = require('fs');\n const EventEmitter = require('events').EventEmitter;\n const path = require('path');\n+const bootstrap = require('./bootstrap.js');\n \n // TODO: Support running on Windows?\n-const permissions_file = '../' + path.join('conf', conf.permissions_file);\n-\n+const permissions_file = path.join(__dirname,'..','conf', conf.permissions_file);\n // We could probably do this without\n // using the EventEmitter parent\n // but it lets us do the events\n class Permissions extends EventEmitter {\n     // FRONT END\n-    getRoles() {\n-        return this.roles;\n+    addCommandToRole(guildId, commandName, roleId, userId){\n+        // If the issuing user has the server permission \"Administrator\", they\n+        // can add any command to any role. Otherwise the issuing user must\n+        // have the server permission to manage roles/permissions. The role they\n+        // wish to alter must be lower than their highest role and they must\n+        // already have the permission to run the command.\n+        let changed = false; // Tracks if we made any changes\n+        let guild = this.getGuildById(guildId); // Get the guild obj\n+        let member = this.getMember(guild,userId); // Get the issuer member obj\n+        let message = ''; // Holds output of our success or failure\n+\n+        if (member.hasPermission('MANAGE_ROLES_OR_PERMISSIONS') || member.hasPermission('ADMINISTRATOR')) {\n+            // Get the role obj for the role they wish to alter\n+            let roleChanging = guild.roles.get(roleId);\n+            if(member.highestRole.comparePositionTo(roleChanging)>0 || member.hasPermission('ADMINISTRATOR')){\n+                if(this.isAllowedToRun(commandName, member.roles, guild) || member.hasPermission('ADMINISTRATOR')){\n+                    if(guildId && commandName && roleId){\n+                        // We are allowed to add this command to the role\n+                        // add it if it isn't already, initializing as needed\n+                        if(!this.permissions[guildId]){\n+                            // We haven't seen this Guild Id yet\n+                            this.permissions[guildId]={};\n+                        }\n+                        if(!this.permissions[guildId][commandName]){\n+                            // We haven't seen this command name yet, make a new array\n+                            this.permissions[guildId][commandName] = new Array(roleId);\n+                            changed = true;\n+                        } else {\n+                            // Check if this command already has this role\n+                            if(this.permissions[guildId][commandName].indexOf(roleId)===-1){\n+                                // Didn't have the role yet, add it to the array\n+                                this.permissions[guildId][commandName].push(roleId);\n+                                changed = true;\n+                            } else {\n+                                message = '\"'+commandName+'\" already granted';\n+                            }\n+                        }\n+                        if(changed){\n+                            message = 'Granted \"'+commandName+'\"';\n+                            this.save();\n+                        }\n+                    }\n+                } else {\n+                    message = 'Unable to grant \"'+commandName+'\". You must already be allowed to run this command or have the server permission \"Administrator\" to grant';\n+                }\n+            } else {\n+                message = 'Unable to grant \"'+commandName+'\". You can only alter roles lower than your highest role or have the server permission \"Administrator\" to grant';\n+            }\n+        } else {\n+                message = 'Unable to grant \"'+commandName+'\". You must have the server permission \"Administrator\" or \"Manage Permissions\"';\n+        }\n+        return message;\n     }\n-\n-    addRole(role) {\n-        // We only add the role if it was never created before\n-        if (!this.roles.role) {\n-            this.roles[role] = [];\n+    getGuildById(guildId){\n+        return bootstrap.durendal.bot.guilds.get(guildId);\n+    }\n+    getMember(guild, userId){\n+        let result = '';\n+        if(guild){\n+            result = guild.members.get(userId);\n         }\n-\n-        // Why save if we didn't add anyone to the role?\n-        return true;\n+        return result;\n     }\n-\n-    addUser(role, user) {\n-        if (!this.roles.role) {\n-            // Throw exception instead?\n-            this.addRole(role);\n+    // Returns the role Ids that can run the command name in the given guild\n+    getAllowedRoles(guildId, commandName){\n+        let result = [];\n+        // Make sure the permissions object is defined\n+        if(this.permissions){\n+            // Does this guild have any commands with permissions defined?\n+            if(this.permissions[guildId]){\n+                // Does this command have any permissions defined?\n+                if(this.permissions[guildId][commandName]){\n+                    result = this.permissions[guildId][commandName];\n+                }\n+            }\n         }\n-\n-        this.roles[role].push(user);\n-        console.log(this.roles[role]);\n-        delete this.users[user]; // invalidate their roles 'cache'\n-\n-        // Let the object know that we updated something\n-        this.emit('updated');\n+        return result;\n     }\n-\n-    roleHasUser(role, user) {\n-        if (!this.roles.role) {\n-            return false;\n+    // Determines if the provided roles in the provided guild have permission\n+    // to run the provided command name. True if yes, false otherwise\n+    isAllowedToRun(commandName, runnersRoles, runnersGuild){\n+        let foundAnAllowedRole = false;\n+        if(runnersGuild && runnersRoles){\n+            // Get the role Ids that can execute this command\n+            let allowedRoles = this.getAllowedRoles(runnersGuild.id, commandName);\n+            // Look through all unless we find one that matches our provided roles\n+            if(allowedRoles.length>0 && !foundAnAllowedRole){\n+                for(var i=0;i<allowedRoles.length && !foundAnAllowedRole;i++){\n+                    if(runnersRoles.has(allowedRoles[i])){\n+                        // We found a role that we have and is allowed to run\n+                        foundAnAllowedRole = true;\n+                    }\n+                }\n+            }\n         }\n-\n-        // if (!this.roles.)\n+        return foundAnAllowedRole;\n     }\n \n-    getRoles(user) {\n+    removeCommandFromRole(guildId, commandName, roleId, userId){\n+\n+        let changed = false;\n+        let guild = this.getGuildById(guildId); // Get the guild obj\n+        let member = this.getMember(guild,userId); // Get the issuer member obj\n+        let message = ''; // Holds output of our success or failure\n+\n+        if (member.hasPermission('MANAGE_ROLES_OR_PERMISSIONS')\n+            || member.hasPermission('ADMINISTRATOR')) {\n+            // Get the role obj for the role they wish to alter\n+            let roleChanging = guild.roles.get(roleId);\n+            if(member.highestRole.comparePositionTo(roleChanging)>0 || member.hasPermission('ADMINISTRATOR')){","path":"src/permissions.js","position":153,"original_position":153,"commit_id":"bc687161f58cd7994e6819ab5c7feb5370959cef","original_commit_id":"bc687161f58cd7994e6819ab5c7feb5370959cef","user":{"login":"adigitalmonk","id":2956701,"avatar_url":"https://avatars.githubusercontent.com/u/2956701?v=3","gravatar_id":"","url":"https://api.github.com/users/adigitalmonk","html_url":"https://github.com/adigitalmonk","followers_url":"https://api.github.com/users/adigitalmonk/followers","following_url":"https://api.github.com/users/adigitalmonk/following{/other_user}","gists_url":"https://api.github.com/users/adigitalmonk/gists{/gist_id}","starred_url":"https://api.github.com/users/adigitalmonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/adigitalmonk/subscriptions","organizations_url":"https://api.github.com/users/adigitalmonk/orgs","repos_url":"https://api.github.com/users/adigitalmonk/repos","events_url":"https://api.github.com/users/adigitalmonk/events{/privacy}","received_events_url":"https://api.github.com/users/adigitalmonk/received_events","type":"User","site_admin":false},"body":"I kind of hate this unending chain of `if`s, is there a saner way to write this?","created_at":"2016-11-30T02:05:49Z","updated_at":"2016-11-30T02:05:49Z","html_url":"https://github.com/adigitalmonk/durendal-bot/pull/40#discussion_r90156741","pull_request_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40","_links":{"self":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/comments/90156741"},"html":{"href":"https://github.com/adigitalmonk/durendal-bot/pull/40#discussion_r90156741"},"pull_request":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40"}}},"pull_request":{"url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40","id":95811933,"html_url":"https://github.com/adigitalmonk/durendal-bot/pull/40","diff_url":"https://github.com/adigitalmonk/durendal-bot/pull/40.diff","patch_url":"https://github.com/adigitalmonk/durendal-bot/pull/40.patch","issue_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/40","number":40,"state":"open","locked":false,"title":"Revised permission infastructure","user":{"login":"dmasterson","id":2954784,"avatar_url":"https://avatars.githubusercontent.com/u/2954784?v=3","gravatar_id":"","url":"https://api.github.com/users/dmasterson","html_url":"https://github.com/dmasterson","followers_url":"https://api.github.com/users/dmasterson/followers","following_url":"https://api.github.com/users/dmasterson/following{/other_user}","gists_url":"https://api.github.com/users/dmasterson/gists{/gist_id}","starred_url":"https://api.github.com/users/dmasterson/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/dmasterson/subscriptions","organizations_url":"https://api.github.com/users/dmasterson/orgs","repos_url":"https://api.github.com/users/dmasterson/repos","events_url":"https://api.github.com/users/dmasterson/events{/privacy}","received_events_url":"https://api.github.com/users/dmasterson/received_events","type":"User","site_admin":false},"body":"This revises and expands on the permissions object. Permissions are based on Discord server roles. Commands that are restricted must be associated with a guilds server role(s). Additional data members were added to the command base class which should be relevant to more than just the new commands this commit introduces. The message listener was also changed to allow the bot to respond to Direct Messages. A potentially breaking change was introduced by changing a variable name, but I believe the result is much clearer long term.","created_at":"2016-11-30T01:38:54Z","updated_at":"2016-11-30T02:05:49Z","closed_at":null,"merged_at":null,"merge_commit_sha":"5bcdade6bcd649c6761864d1ac90c00a6397b02d","assignee":null,"assignees":[],"milestone":null,"commits_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40/commits","review_comments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40/comments","review_comment_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/comments{/number}","comments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/40/comments","statuses_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/statuses/bc687161f58cd7994e6819ab5c7feb5370959cef","head":{"label":"adigitalmonk:server-rbp","ref":"server-rbp","sha":"bc687161f58cd7994e6819ab5c7feb5370959cef","user":{"login":"adigitalmonk","id":2956701,"avatar_url":"https://avatars.githubusercontent.com/u/2956701?v=3","gravatar_id":"","url":"https://api.github.com/users/adigitalmonk","html_url":"https://github.com/adigitalmonk","followers_url":"https://api.github.com/users/adigitalmonk/followers","following_url":"https://api.github.com/users/adigitalmonk/following{/other_user}","gists_url":"https://api.github.com/users/adigitalmonk/gists{/gist_id}","starred_url":"https://api.github.com/users/adigitalmonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/adigitalmonk/subscriptions","organizations_url":"https://api.github.com/users/adigitalmonk/orgs","repos_url":"https://api.github.com/users/adigitalmonk/repos","events_url":"https://api.github.com/users/adigitalmonk/events{/privacy}","received_events_url":"https://api.github.com/users/adigitalmonk/received_events","type":"User","site_admin":false},"repo":{"id":72796368,"name":"durendal-bot","full_name":"adigitalmonk/durendal-bot","owner":{"login":"adigitalmonk","id":2956701,"avatar_url":"https://avatars.githubusercontent.com/u/2956701?v=3","gravatar_id":"","url":"https://api.github.com/users/adigitalmonk","html_url":"https://github.com/adigitalmonk","followers_url":"https://api.github.com/users/adigitalmonk/followers","following_url":"https://api.github.com/users/adigitalmonk/following{/other_user}","gists_url":"https://api.github.com/users/adigitalmonk/gists{/gist_id}","starred_url":"https://api.github.com/users/adigitalmonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/adigitalmonk/subscriptions","organizations_url":"https://api.github.com/users/adigitalmonk/orgs","repos_url":"https://api.github.com/users/adigitalmonk/repos","events_url":"https://api.github.com/users/adigitalmonk/events{/privacy}","received_events_url":"https://api.github.com/users/adigitalmonk/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/adigitalmonk/durendal-bot","description":"DiscordAPI Bot for the Durendal Gaming Discord Server","fork":false,"url":"https://api.github.com/repos/adigitalmonk/durendal-bot","forks_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/forks","keys_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/keys{/key_id}","collaborators_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/teams","hooks_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/hooks","issue_events_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/events{/number}","events_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/events","assignees_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/assignees{/user}","branches_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/branches{/branch}","tags_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/tags","blobs_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/refs{/sha}","trees_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/trees{/sha}","statuses_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/statuses/{sha}","languages_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/languages","stargazers_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/stargazers","contributors_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/contributors","subscribers_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/subscribers","subscription_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/subscription","commits_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/commits{/sha}","git_commits_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/commits{/sha}","comments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/comments{/number}","issue_comment_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/comments{/number}","contents_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/contents/{+path}","compare_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/compare/{base}...{head}","merges_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/merges","archive_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/downloads","issues_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues{/number}","pulls_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls{/number}","milestones_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/milestones{/number}","notifications_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/labels{/name}","releases_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/releases{/id}","deployments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/deployments","created_at":"2016-11-03T23:34:34Z","updated_at":"2016-11-03T23:35:33Z","pushed_at":"2016-11-30T01:53:27Z","git_url":"git://github.com/adigitalmonk/durendal-bot.git","ssh_url":"git@github.com:adigitalmonk/durendal-bot.git","clone_url":"https://github.com/adigitalmonk/durendal-bot.git","svn_url":"https://github.com/adigitalmonk/durendal-bot","homepage":null,"size":48,"stargazers_count":0,"watchers_count":0,"language":"JavaScript","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":18,"forks":0,"open_issues":18,"watchers":0,"default_branch":"master"}},"base":{"label":"adigitalmonk:master","ref":"master","sha":"7009cd6bd8d566de5ec67ec8065f3781f886721f","user":{"login":"adigitalmonk","id":2956701,"avatar_url":"https://avatars.githubusercontent.com/u/2956701?v=3","gravatar_id":"","url":"https://api.github.com/users/adigitalmonk","html_url":"https://github.com/adigitalmonk","followers_url":"https://api.github.com/users/adigitalmonk/followers","following_url":"https://api.github.com/users/adigitalmonk/following{/other_user}","gists_url":"https://api.github.com/users/adigitalmonk/gists{/gist_id}","starred_url":"https://api.github.com/users/adigitalmonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/adigitalmonk/subscriptions","organizations_url":"https://api.github.com/users/adigitalmonk/orgs","repos_url":"https://api.github.com/users/adigitalmonk/repos","events_url":"https://api.github.com/users/adigitalmonk/events{/privacy}","received_events_url":"https://api.github.com/users/adigitalmonk/received_events","type":"User","site_admin":false},"repo":{"id":72796368,"name":"durendal-bot","full_name":"adigitalmonk/durendal-bot","owner":{"login":"adigitalmonk","id":2956701,"avatar_url":"https://avatars.githubusercontent.com/u/2956701?v=3","gravatar_id":"","url":"https://api.github.com/users/adigitalmonk","html_url":"https://github.com/adigitalmonk","followers_url":"https://api.github.com/users/adigitalmonk/followers","following_url":"https://api.github.com/users/adigitalmonk/following{/other_user}","gists_url":"https://api.github.com/users/adigitalmonk/gists{/gist_id}","starred_url":"https://api.github.com/users/adigitalmonk/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/adigitalmonk/subscriptions","organizations_url":"https://api.github.com/users/adigitalmonk/orgs","repos_url":"https://api.github.com/users/adigitalmonk/repos","events_url":"https://api.github.com/users/adigitalmonk/events{/privacy}","received_events_url":"https://api.github.com/users/adigitalmonk/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/adigitalmonk/durendal-bot","description":"DiscordAPI Bot for the Durendal Gaming Discord Server","fork":false,"url":"https://api.github.com/repos/adigitalmonk/durendal-bot","forks_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/forks","keys_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/keys{/key_id}","collaborators_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/teams","hooks_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/hooks","issue_events_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/events{/number}","events_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/events","assignees_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/assignees{/user}","branches_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/branches{/branch}","tags_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/tags","blobs_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/refs{/sha}","trees_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/trees{/sha}","statuses_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/statuses/{sha}","languages_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/languages","stargazers_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/stargazers","contributors_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/contributors","subscribers_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/subscribers","subscription_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/subscription","commits_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/commits{/sha}","git_commits_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/git/commits{/sha}","comments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/comments{/number}","issue_comment_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/comments{/number}","contents_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/contents/{+path}","compare_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/compare/{base}...{head}","merges_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/merges","archive_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/downloads","issues_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues{/number}","pulls_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls{/number}","milestones_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/milestones{/number}","notifications_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/labels{/name}","releases_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/releases{/id}","deployments_url":"https://api.github.com/repos/adigitalmonk/durendal-bot/deployments","created_at":"2016-11-03T23:34:34Z","updated_at":"2016-11-03T23:35:33Z","pushed_at":"2016-11-30T01:53:27Z","git_url":"git://github.com/adigitalmonk/durendal-bot.git","ssh_url":"git@github.com:adigitalmonk/durendal-bot.git","clone_url":"https://github.com/adigitalmonk/durendal-bot.git","svn_url":"https://github.com/adigitalmonk/durendal-bot","homepage":null,"size":48,"stargazers_count":0,"watchers_count":0,"language":"JavaScript","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":18,"forks":0,"open_issues":18,"watchers":0,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40"},"html":{"href":"https://github.com/adigitalmonk/durendal-bot/pull/40"},"issue":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/40"},"comments":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/issues/40/comments"},"review_comments":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40/comments"},"review_comment":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/pulls/40/commits"},"statuses":{"href":"https://api.github.com/repos/adigitalmonk/durendal-bot/statuses/bc687161f58cd7994e6819ab5c7feb5370959cef"}}}}
{"actor":{"display_login":"adigitalmonk"}}