{"action":"created","comment":{"url":"https://api.github.com/repos/thecartercenter/elmo/pulls/comments/192745390","pull_request_review_id":125578262,"id":192745390,"node_id":"MDI0OlB1bGxSZXF1ZXN0UmV2aWV3Q29tbWVudDE5Mjc0NTM5MA==","diff_hunk":"@@ -0,0 +1,249 @@\n+class Sms::AnswerParser\n+  class ParseError < Sms::Error\n+    attr_reader :type, :params\n+\n+    def initialize(type, params = {})\n+      super(type)\n+      @type = type\n+      @params = params\n+    end\n+\n+    def to_s\n+      super + \" #{@params.inspect}\"\n+    end\n+  end\n+\n+  class Answer < Struct.new(:rank, :value)\n+    def parse(qing)\n+      case qing.question.qtype.name\n+      when \"integer\", \"counter\"\n+        # for integer question, make sure the value looks like a number\n+        raise_parse_error(\"answer_not_integer\") unless value =~ /\\A\\d+\\z/\n+\n+        # number must be in range\n+        val_f = value.to_f\n+        question = qing.question\n+        if question.maximum && (val_f > question.maximum || question.maxstrictly && val_f == question.maximum)\n+          raise_parse_error(\"answer_too_large\", { maximum: question.maximum })\n+        end\n+        if question.minimum && (val_f < question.minimum || question.minstrictly && val_f == question.minimum)\n+          raise_parse_error(\"answer_too_small\", { minumum: question.minimum })\n+        end\n+\n+        # add to response\n+        build_answer(qing, value: value)\n+\n+      when \"decimal\"\n+        # for integer question, make sure the value looks like a number\n+        raise_parse_error(\"answer_not_decimal\") unless value =~ /\\A[\\d]+([\\.,][\\d]+)?\\z/\n+\n+        # add to response\n+        build_answer(qing, value: value)\n+\n+      when \"select_one\"\n+        if qing.sms_formatting_as_text?\n+          option = qing.option_set.all_options.by_canonical_name(value).first\n+          raise_parse_error(\"answer_not_valid_option\") unless option\n+          build_answer(qing, qing.option_set.path_to_option(option).map { |o| {option: o} }, multilevel: qing.multilevel?)\n+\n+        elsif qing.sms_formatting_as_appendix?\n+          option = qing.option_set.fetch_by_shortcode(value.downcase).try(:option)\n+          raise_parse_error(\"answer_not_valid_option\") unless option\n+          build_answer(qing, qing.option_set.path_to_option(option).map { |o| {option: o} }, multilevel: qing.multilevel?)\n+\n+        else\n+          # make sure the value is a letter(s)\n+          raise_parse_error(\"answer_not_valid_option\") unless value =~ /\\A[a-z]+\\z/i\n+\n+          # convert to number (1-based)\n+          idx = letters_to_index(value.downcase)\n+\n+          # make sure it makes sense for the option set\n+          raise_parse_error(\"answer_not_valid_option\") if idx > qing.question.options.size\n+\n+          # if we get to here, we're good, so add\n+          build_answer(qing, option: qing.question.options[idx-1])\n+        end\n+\n+      when \"select_multiple\"\n+        # case insensitive\n+        self.value.downcase!\n+\n+        # hopefully this stays empty!\n+        invalid = []\n+\n+        # split options\n+\n+        # if the option set has no commas, and has <= 26 options, assume it's a legacy submission\n+        # and split on spaces, otherwise split on commas\n+        if qing.option_set.descendants.count <= 26 && value =~ /\\A[A-Z]+\\z/i\n+          raise_parse_error(\"answer_not_valid_long_option_multi\") if value.length > 10\n+          split_options = value.split(\"\")\n+        else\n+          split_options = value.split(/\\s*,\\s*/)\n+        end\n+\n+        if qing.option_set.sms_formatting == \"appendix\"\n+          # fetch each option by shortcode\n+          idxs = split_options.map do |l|\n+            option = qing.option_set.fetch_by_shortcode(l).try(:option)\n+            # make sure an option was found\n+            if option.present?\n+              # convert to an index\n+              option_to_index(option, qing)\n+            # otherwise add to invalid and return nonsense index\n+            else\n+              invalid << l unless option.present?\n+              -1\n+            end\n+          end\n+        else\n+          # deal with each option, accumulating a list of indices\n+          idxs = split_options.map do |l|\n+\n+            # make sure it's a letter\n+            if l =~ /\\A[a-z]\\z/i\n+\n+              # convert to an index\n+              idx = letters_to_index(l)\n+\n+              # make sure this index makes sense for the option set\n+              invalid << l if idx > qing.question.options.size\n+\n+              idx\n+\n+            # otherwise add to invalid and return a nonsense index\n+            else\n+              invalid << l\n+              -1\n+            end\n+          end\n+        end\n+\n+        # raise appropriate error if we found invalid answer(s)\n+        if invalid.size > 1\n+          raise_parse_error(\"answer_not_valid_options_multi\", value: value, invalid_options: invalid.join(\", \"))\n+        elsif invalid.size == 1\n+          raise_parse_error(\"answer_not_valid_option_multi\", value: value, invalid_options: invalid.first)\n+        end\n+\n+        # if we get to here, we're good, so add\n+        build_answer(qing, choices: idxs.map { |idx| Choice.new(option: qing.question.options[idx-1]) })\n+\n+      when \"text\", \"long_text\"\n+        build_answer(qing, value: value)\n+\n+      when \"date\"\n+        # error if too short (must be at least 8 chars)\n+        raise_parse_error(\"answer_not_date\", value: value) if value.size < 8\n+\n+        # try to parse date\n+        begin\n+          self.value = Date.parse(value)\n+        rescue ArgumentError\n+          raise_parse_error(\"answer_not_date\", value: value)\n+        end\n+\n+        # if we get to here, we're good, so add\n+        build_answer(qing, date_value: value)\n+\n+      when \"time\"\n+        # error if too long or too short (must be 3 or 4 digits)\n+        digits = value.gsub(/[^\\d]/, \"\")\n+        raise_parse_error(\"answer_not_time\", value: value) if digits.size < 3 || digits.size > 4\n+\n+        # try to parse time\n+        begin\n+          # add a colon before the last two digits (if needed) and add UTC so timezone doesn't mess things up\n+          with_colon = value.gsub(/(\\d{1,2})[\\.,]?(\\d{2})/) { \"#{$1}:#{$2}\" }\n+          self.value = Time.parse(with_colon + \" UTC\")\n+        rescue ArgumentError\n+          raise_parse_error(\"answer_not_time\", value: value)\n+        end\n+\n+        # if we get to here, we're good, so add\n+        build_answer(qing, time_value: value)\n+\n+      when \"datetime\"\n+        # error if too long or too short (must be between 9 and 12 digits)\n+        digits = value.gsub(/[^\\d]/, \"\")\n+        raise_parse_error(\"answer_not_datetime\", value: value) if digits.size < 9 || digits.size > 12\n+\n+        # try to parse datetime\n+        begin\n+          # if we have a string of 12 straight digits, leave it alone\n+          if value =~ /\\A\\d{12}\\z/\n+            to_parse = value\n+          else\n+            # otherwise add a colon before the last two digits of the time (if needed) to help with parsing\n+            # also replace any .'s or ,'s or ;'s as they don't work so well\n+            to_parse = value.gsub(/(\\d{1,2})[\\.,;]?(\\d{2})[a-z\\s]*$/) { \"#{$1}:#{$2}\" }\n+          end\n+          self.value = Time.zone.parse(to_parse)\n+        rescue ArgumentError\n+          raise_parse_error(\"answer_not_datetime\", value: value)\n+        end\n+\n+        # if we get to here, we're good, so add\n+        build_answer(qing, datetime_value: value)\n+      end\n+    end\n+\n+    private\n+\n+    # converts a series of letters to the corresponding index, e.g. a => 1, b => 2, z => 26, aa => 27, etc.\n+    def letters_to_index(letters)\n+      sum = 0\n+      letters.split(\"\").each_with_index do |letter, i|\n+        sum += (letter.ord - 96) * (26 ** (letters.size - i - 1))\n+      end\n+      sum\n+    end\n+\n+    def option_to_index(option, qing)\n+      # add one because of how letter indexes are counted\n+      qing.question.options.index { |o| o.id == option.id } + 1\n+    end\n+\n+    def build_answer(qing, attribs_set, options = {})\n+      Array.wrap(attribs_set).each_with_index.map do |attribs, idx|\n+        attribs.merge(\n+          rank: options[:multilevel] ? idx + 1 : 1,\n+          questioning_id: qing.id)\n+      end\n+    end\n+\n+    def raise_parse_error(type, options = {})\n+      raise ParseError.new(type, options)\n+    end\n+  end\n+\n+  include Enumerable\n+  attr_reader :answers\n+  delegate :each, to: :answers\n+\n+  def initialize(tokens)","path":"app/models/sms/answer_parser.rb","position":225,"original_position":225,"commit_id":"0f40226a2f710117b19d5627198974547d9b9720","original_commit_id":"0f40226a2f710117b19d5627198974547d9b9720","user":{"login":"houndci-bot","id":6697940,"node_id":"MDQ6VXNlcjY2OTc5NDA=","avatar_url":"https://avatars0.githubusercontent.com/u/6697940?v=4","gravatar_id":"","url":"https://api.github.com/users/houndci-bot","html_url":"https://github.com/houndci-bot","followers_url":"https://api.github.com/users/houndci-bot/followers","following_url":"https://api.github.com/users/houndci-bot/following{/other_user}","gists_url":"https://api.github.com/users/houndci-bot/gists{/gist_id}","starred_url":"https://api.github.com/users/houndci-bot/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/houndci-bot/subscriptions","organizations_url":"https://api.github.com/users/houndci-bot/orgs","repos_url":"https://api.github.com/users/houndci-bot/repos","events_url":"https://api.github.com/users/houndci-bot/events{/privacy}","received_events_url":"https://api.github.com/users/houndci-bot/received_events","type":"User","site_admin":false},"body":"Metrics/MethodLength: Method has too many lines. [15/10]","created_at":"2018-06-04T13:43:21Z","updated_at":"2018-06-04T13:43:22Z","html_url":"https://github.com/thecartercenter/elmo/pull/450#discussion_r192745390","pull_request_url":"https://api.github.com/repos/thecartercenter/elmo/pulls/450","author_association":"NONE","_links":{"self":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/comments/192745390"},"html":{"href":"https://github.com/thecartercenter/elmo/pull/450#discussion_r192745390"},"pull_request":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/450"}}},"pull_request":{"url":"https://api.github.com/repos/thecartercenter/elmo/pulls/450","id":192412552,"node_id":"MDExOlB1bGxSZXF1ZXN0MTkyNDEyNTUy","html_url":"https://github.com/thecartercenter/elmo/pull/450","diff_url":"https://github.com/thecartercenter/elmo/pull/450.diff","patch_url":"https://github.com/thecartercenter/elmo/pull/450.patch","issue_url":"https://api.github.com/repos/thecartercenter/elmo/issues/450","number":450,"state":"open","locked":false,"title":"8184 sms answer hierarchy","user":{"login":"scttnlsn","id":578446,"node_id":"MDQ6VXNlcjU3ODQ0Ng==","avatar_url":"https://avatars2.githubusercontent.com/u/578446?v=4","gravatar_id":"","url":"https://api.github.com/users/scttnlsn","html_url":"https://github.com/scttnlsn","followers_url":"https://api.github.com/users/scttnlsn/followers","following_url":"https://api.github.com/users/scttnlsn/following{/other_user}","gists_url":"https://api.github.com/users/scttnlsn/gists{/gist_id}","starred_url":"https://api.github.com/users/scttnlsn/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/scttnlsn/subscriptions","organizations_url":"https://api.github.com/users/scttnlsn/orgs","repos_url":"https://api.github.com/users/scttnlsn/repos","events_url":"https://api.github.com/users/scttnlsn/events{/privacy}","received_events_url":"https://api.github.com/users/scttnlsn/received_events","type":"User","site_admin":false},"body":"","created_at":"2018-06-04T13:43:00Z","updated_at":"2018-06-04T13:43:22Z","closed_at":null,"merged_at":null,"merge_commit_sha":"3a221d0f656dcbf43f092196c054a65a05927bba","assignee":null,"assignees":[],"requested_reviewers":[{"login":"smoyth","id":702320,"node_id":"MDQ6VXNlcjcwMjMyMA==","avatar_url":"https://avatars1.githubusercontent.com/u/702320?v=4","gravatar_id":"","url":"https://api.github.com/users/smoyth","html_url":"https://github.com/smoyth","followers_url":"https://api.github.com/users/smoyth/followers","following_url":"https://api.github.com/users/smoyth/following{/other_user}","gists_url":"https://api.github.com/users/smoyth/gists{/gist_id}","starred_url":"https://api.github.com/users/smoyth/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/smoyth/subscriptions","organizations_url":"https://api.github.com/users/smoyth/orgs","repos_url":"https://api.github.com/users/smoyth/repos","events_url":"https://api.github.com/users/smoyth/events{/privacy}","received_events_url":"https://api.github.com/users/smoyth/received_events","type":"User","site_admin":false}],"requested_teams":[],"labels":[],"milestone":null,"commits_url":"https://api.github.com/repos/thecartercenter/elmo/pulls/450/commits","review_comments_url":"https://api.github.com/repos/thecartercenter/elmo/pulls/450/comments","review_comment_url":"https://api.github.com/repos/thecartercenter/elmo/pulls/comments{/number}","comments_url":"https://api.github.com/repos/thecartercenter/elmo/issues/450/comments","statuses_url":"https://api.github.com/repos/thecartercenter/elmo/statuses/0f40226a2f710117b19d5627198974547d9b9720","head":{"label":"thecartercenter:8184_sms_answer_hierarchy","ref":"8184_sms_answer_hierarchy","sha":"0f40226a2f710117b19d5627198974547d9b9720","user":{"login":"thecartercenter","id":5075178,"node_id":"MDEyOk9yZ2FuaXphdGlvbjUwNzUxNzg=","avatar_url":"https://avatars1.githubusercontent.com/u/5075178?v=4","gravatar_id":"","url":"https://api.github.com/users/thecartercenter","html_url":"https://github.com/thecartercenter","followers_url":"https://api.github.com/users/thecartercenter/followers","following_url":"https://api.github.com/users/thecartercenter/following{/other_user}","gists_url":"https://api.github.com/users/thecartercenter/gists{/gist_id}","starred_url":"https://api.github.com/users/thecartercenter/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thecartercenter/subscriptions","organizations_url":"https://api.github.com/users/thecartercenter/orgs","repos_url":"https://api.github.com/users/thecartercenter/repos","events_url":"https://api.github.com/users/thecartercenter/events{/privacy}","received_events_url":"https://api.github.com/users/thecartercenter/received_events","type":"Organization","site_admin":false},"repo":{"id":11615188,"node_id":"MDEwOlJlcG9zaXRvcnkxMTYxNTE4OA==","name":"elmo","full_name":"thecartercenter/elmo","owner":{"login":"thecartercenter","id":5075178,"node_id":"MDEyOk9yZ2FuaXphdGlvbjUwNzUxNzg=","avatar_url":"https://avatars1.githubusercontent.com/u/5075178?v=4","gravatar_id":"","url":"https://api.github.com/users/thecartercenter","html_url":"https://github.com/thecartercenter","followers_url":"https://api.github.com/users/thecartercenter/followers","following_url":"https://api.github.com/users/thecartercenter/following{/other_user}","gists_url":"https://api.github.com/users/thecartercenter/gists{/gist_id}","starred_url":"https://api.github.com/users/thecartercenter/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thecartercenter/subscriptions","organizations_url":"https://api.github.com/users/thecartercenter/orgs","repos_url":"https://api.github.com/users/thecartercenter/repos","events_url":"https://api.github.com/users/thecartercenter/events{/privacy}","received_events_url":"https://api.github.com/users/thecartercenter/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/thecartercenter/elmo","description":" ELMO is a mobile data collection and analysis web application.","fork":false,"url":"https://api.github.com/repos/thecartercenter/elmo","forks_url":"https://api.github.com/repos/thecartercenter/elmo/forks","keys_url":"https://api.github.com/repos/thecartercenter/elmo/keys{/key_id}","collaborators_url":"https://api.github.com/repos/thecartercenter/elmo/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/thecartercenter/elmo/teams","hooks_url":"https://api.github.com/repos/thecartercenter/elmo/hooks","issue_events_url":"https://api.github.com/repos/thecartercenter/elmo/issues/events{/number}","events_url":"https://api.github.com/repos/thecartercenter/elmo/events","assignees_url":"https://api.github.com/repos/thecartercenter/elmo/assignees{/user}","branches_url":"https://api.github.com/repos/thecartercenter/elmo/branches{/branch}","tags_url":"https://api.github.com/repos/thecartercenter/elmo/tags","blobs_url":"https://api.github.com/repos/thecartercenter/elmo/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/thecartercenter/elmo/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/thecartercenter/elmo/git/refs{/sha}","trees_url":"https://api.github.com/repos/thecartercenter/elmo/git/trees{/sha}","statuses_url":"https://api.github.com/repos/thecartercenter/elmo/statuses/{sha}","languages_url":"https://api.github.com/repos/thecartercenter/elmo/languages","stargazers_url":"https://api.github.com/repos/thecartercenter/elmo/stargazers","contributors_url":"https://api.github.com/repos/thecartercenter/elmo/contributors","subscribers_url":"https://api.github.com/repos/thecartercenter/elmo/subscribers","subscription_url":"https://api.github.com/repos/thecartercenter/elmo/subscription","commits_url":"https://api.github.com/repos/thecartercenter/elmo/commits{/sha}","git_commits_url":"https://api.github.com/repos/thecartercenter/elmo/git/commits{/sha}","comments_url":"https://api.github.com/repos/thecartercenter/elmo/comments{/number}","issue_comment_url":"https://api.github.com/repos/thecartercenter/elmo/issues/comments{/number}","contents_url":"https://api.github.com/repos/thecartercenter/elmo/contents/{+path}","compare_url":"https://api.github.com/repos/thecartercenter/elmo/compare/{base}...{head}","merges_url":"https://api.github.com/repos/thecartercenter/elmo/merges","archive_url":"https://api.github.com/repos/thecartercenter/elmo/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/thecartercenter/elmo/downloads","issues_url":"https://api.github.com/repos/thecartercenter/elmo/issues{/number}","pulls_url":"https://api.github.com/repos/thecartercenter/elmo/pulls{/number}","milestones_url":"https://api.github.com/repos/thecartercenter/elmo/milestones{/number}","notifications_url":"https://api.github.com/repos/thecartercenter/elmo/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/thecartercenter/elmo/labels{/name}","releases_url":"https://api.github.com/repos/thecartercenter/elmo/releases{/id}","deployments_url":"https://api.github.com/repos/thecartercenter/elmo/deployments","created_at":"2013-07-23T17:56:04Z","updated_at":"2018-06-03T11:04:01Z","pushed_at":"2018-06-04T13:43:00Z","git_url":"git://github.com/thecartercenter/elmo.git","ssh_url":"git@github.com:thecartercenter/elmo.git","clone_url":"https://github.com/thecartercenter/elmo.git","svn_url":"https://github.com/thecartercenter/elmo","homepage":"https://getelmo.org","size":72970,"stargazers_count":34,"watchers_count":34,"language":"Ruby","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":38,"mirror_url":null,"archived":false,"open_issues_count":4,"license":{"key":"apache-2.0","name":"Apache License 2.0","spdx_id":"Apache-2.0","url":"https://api.github.com/licenses/apache-2.0","node_id":"MDc6TGljZW5zZTI="},"forks":38,"open_issues":4,"watchers":34,"default_branch":"develop"}},"base":{"label":"thecartercenter:develop","ref":"develop","sha":"6ab8076cd53d681cc1286848ad50ceed0dab0e84","user":{"login":"thecartercenter","id":5075178,"node_id":"MDEyOk9yZ2FuaXphdGlvbjUwNzUxNzg=","avatar_url":"https://avatars1.githubusercontent.com/u/5075178?v=4","gravatar_id":"","url":"https://api.github.com/users/thecartercenter","html_url":"https://github.com/thecartercenter","followers_url":"https://api.github.com/users/thecartercenter/followers","following_url":"https://api.github.com/users/thecartercenter/following{/other_user}","gists_url":"https://api.github.com/users/thecartercenter/gists{/gist_id}","starred_url":"https://api.github.com/users/thecartercenter/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thecartercenter/subscriptions","organizations_url":"https://api.github.com/users/thecartercenter/orgs","repos_url":"https://api.github.com/users/thecartercenter/repos","events_url":"https://api.github.com/users/thecartercenter/events{/privacy}","received_events_url":"https://api.github.com/users/thecartercenter/received_events","type":"Organization","site_admin":false},"repo":{"id":11615188,"node_id":"MDEwOlJlcG9zaXRvcnkxMTYxNTE4OA==","name":"elmo","full_name":"thecartercenter/elmo","owner":{"login":"thecartercenter","id":5075178,"node_id":"MDEyOk9yZ2FuaXphdGlvbjUwNzUxNzg=","avatar_url":"https://avatars1.githubusercontent.com/u/5075178?v=4","gravatar_id":"","url":"https://api.github.com/users/thecartercenter","html_url":"https://github.com/thecartercenter","followers_url":"https://api.github.com/users/thecartercenter/followers","following_url":"https://api.github.com/users/thecartercenter/following{/other_user}","gists_url":"https://api.github.com/users/thecartercenter/gists{/gist_id}","starred_url":"https://api.github.com/users/thecartercenter/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thecartercenter/subscriptions","organizations_url":"https://api.github.com/users/thecartercenter/orgs","repos_url":"https://api.github.com/users/thecartercenter/repos","events_url":"https://api.github.com/users/thecartercenter/events{/privacy}","received_events_url":"https://api.github.com/users/thecartercenter/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/thecartercenter/elmo","description":" ELMO is a mobile data collection and analysis web application.","fork":false,"url":"https://api.github.com/repos/thecartercenter/elmo","forks_url":"https://api.github.com/repos/thecartercenter/elmo/forks","keys_url":"https://api.github.com/repos/thecartercenter/elmo/keys{/key_id}","collaborators_url":"https://api.github.com/repos/thecartercenter/elmo/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/thecartercenter/elmo/teams","hooks_url":"https://api.github.com/repos/thecartercenter/elmo/hooks","issue_events_url":"https://api.github.com/repos/thecartercenter/elmo/issues/events{/number}","events_url":"https://api.github.com/repos/thecartercenter/elmo/events","assignees_url":"https://api.github.com/repos/thecartercenter/elmo/assignees{/user}","branches_url":"https://api.github.com/repos/thecartercenter/elmo/branches{/branch}","tags_url":"https://api.github.com/repos/thecartercenter/elmo/tags","blobs_url":"https://api.github.com/repos/thecartercenter/elmo/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/thecartercenter/elmo/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/thecartercenter/elmo/git/refs{/sha}","trees_url":"https://api.github.com/repos/thecartercenter/elmo/git/trees{/sha}","statuses_url":"https://api.github.com/repos/thecartercenter/elmo/statuses/{sha}","languages_url":"https://api.github.com/repos/thecartercenter/elmo/languages","stargazers_url":"https://api.github.com/repos/thecartercenter/elmo/stargazers","contributors_url":"https://api.github.com/repos/thecartercenter/elmo/contributors","subscribers_url":"https://api.github.com/repos/thecartercenter/elmo/subscribers","subscription_url":"https://api.github.com/repos/thecartercenter/elmo/subscription","commits_url":"https://api.github.com/repos/thecartercenter/elmo/commits{/sha}","git_commits_url":"https://api.github.com/repos/thecartercenter/elmo/git/commits{/sha}","comments_url":"https://api.github.com/repos/thecartercenter/elmo/comments{/number}","issue_comment_url":"https://api.github.com/repos/thecartercenter/elmo/issues/comments{/number}","contents_url":"https://api.github.com/repos/thecartercenter/elmo/contents/{+path}","compare_url":"https://api.github.com/repos/thecartercenter/elmo/compare/{base}...{head}","merges_url":"https://api.github.com/repos/thecartercenter/elmo/merges","archive_url":"https://api.github.com/repos/thecartercenter/elmo/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/thecartercenter/elmo/downloads","issues_url":"https://api.github.com/repos/thecartercenter/elmo/issues{/number}","pulls_url":"https://api.github.com/repos/thecartercenter/elmo/pulls{/number}","milestones_url":"https://api.github.com/repos/thecartercenter/elmo/milestones{/number}","notifications_url":"https://api.github.com/repos/thecartercenter/elmo/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/thecartercenter/elmo/labels{/name}","releases_url":"https://api.github.com/repos/thecartercenter/elmo/releases{/id}","deployments_url":"https://api.github.com/repos/thecartercenter/elmo/deployments","created_at":"2013-07-23T17:56:04Z","updated_at":"2018-06-03T11:04:01Z","pushed_at":"2018-06-04T13:43:00Z","git_url":"git://github.com/thecartercenter/elmo.git","ssh_url":"git@github.com:thecartercenter/elmo.git","clone_url":"https://github.com/thecartercenter/elmo.git","svn_url":"https://github.com/thecartercenter/elmo","homepage":"https://getelmo.org","size":72970,"stargazers_count":34,"watchers_count":34,"language":"Ruby","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":38,"mirror_url":null,"archived":false,"open_issues_count":4,"license":{"key":"apache-2.0","name":"Apache License 2.0","spdx_id":"Apache-2.0","url":"https://api.github.com/licenses/apache-2.0","node_id":"MDc6TGljZW5zZTI="},"forks":38,"open_issues":4,"watchers":34,"default_branch":"develop"}},"_links":{"self":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/450"},"html":{"href":"https://github.com/thecartercenter/elmo/pull/450"},"issue":{"href":"https://api.github.com/repos/thecartercenter/elmo/issues/450"},"comments":{"href":"https://api.github.com/repos/thecartercenter/elmo/issues/450/comments"},"review_comments":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/450/comments"},"review_comment":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/thecartercenter/elmo/pulls/450/commits"},"statuses":{"href":"https://api.github.com/repos/thecartercenter/elmo/statuses/0f40226a2f710117b19d5627198974547d9b9720"}},"author_association":"CONTRIBUTOR"}}
{"actor":{"display_login":"houndci-bot"}}