{"action":"created","comment":{"url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/comments/218843916","pull_request_review_id":156872513,"id":218843916,"node_id":"MDI0OlB1bGxSZXF1ZXN0UmV2aWV3Q29tbWVudDIxODg0MzkxNg==","diff_hunk":"@@ -388,4 +424,629 @@ def expect_updated_criteria_coverage_count_eq(expected_count)\n       end\n     end\n   end\n+  describe 'A group' do\n+    before :each do\n+      @grouping = create(:grouping)\n+    end\n+    context 'with two student members' do\n+      before :each do\n+        # should consist of inviter and another student\n+        @membership = create(:accepted_student_membership, user: create(:student, user_name: 'student1'),\n+                                             grouping: @grouping,\n+                                             membership_status: StudentMembership::STATUSES[:accepted])\n+\n+        @inviter_membership = create(:inviter_student_membership, user: create(:student, user_name: 'student2'),\n+                                                     grouping: @grouping,\n+                                                     membership_status: StudentMembership::STATUSES[:inviter])\n+        @inviter = @inviter_membership.user\n+      end\n+\n+      it 'displays for note without seeing an exception' do\n+        expect { @grouping.display_for_note }.not_to raise_error\n+      end\n+\n+      it \"displays group name and students' usernames\" do\n+        expect { @grouping.group_name_with_student_user_names }.not_to raise_error\n+      end\n+\n+      it \"displays comma separated list of students' usernames\" do\n+        expect(@grouping.get_all_students_in_group).to eq('student1, student2')\n+      end\n+\n+      it 'is valid' do\n+        expect(@grouping.student_membership_number).to eq(2)\n+        expect(@grouping.valid?).to be true\n+      end\n+\n+      it 'returns membership status are part of the group' do\n+        student = create(:student)\n+        expect(@grouping.membership_status(student)).to be_nil\n+        expect(@grouping.membership_status(@membership.user)).to eq('accepted')\n+        expect(@grouping.membership_status(@inviter)).to eq('inviter')\n+      end\n+\n+      it 'detects pending members' do\n+        expect(@grouping.pending?(@inviter)).to be false\n+      end\n+\n+      it 'detects the inviter' do\n+        expect(@grouping.is_inviter?(@membership.user)).to be false\n+        expect(@grouping.is_inviter?(@inviter)).to be true\n+      end\n+\n+      it 'is able to remove a member' do\n+        @grouping.remove_member(@membership.id)\n+        expect(@grouping.membership_status(@membership.user)).to be_nil\n+      end\n+\n+      it 'is able to remove the inviter' do\n+        @grouping.remove_member(@inviter_membership.id)\n+        expect(@grouping.membership_status(@inviter)).to be_nil\n+        expect(@grouping.inviter).not_to be_nil\n+      end\n+\n+      it 'is able to report if the grouping is deletable' do\n+        non_inviter = @membership.user\n+        # delete member to have it deletable\n+        @grouping.remove_member(@membership.id)\n+        @grouping.reload\n+        expect(@grouping.accepted_students.size).to eq(1)\n+        # inviter should not be able to delete grouping\n+        expect(@grouping.deletable_by?(@inviter)).to be false\n+        # non-inviter shouldn't be able to delete grouping\n+        if non_inviter.nil?\n+          raise 'No members in this grouping other than the inviter!'\n+        end\n+        expect(@grouping.deletable_by?(non_inviter)).to be false\n+      end\n+    end\n+\n+    context 'with a pending membership' do\n+      before :each do\n+        @student = create(:student_membership,\n+          grouping: @grouping,\n+          membership_status: StudentMembership::STATUSES[:pending]).user\n+      end\n+\n+      it 'detect pending members' do\n+        expect(@grouping.pending?(@student)).to be true\n+      end\n+\n+      it 'return correct membership status' do\n+        expect(@grouping.membership_status(@student)).to eq('pending')\n+      end\n+\n+      it 'be able to decline invitation' do\n+        @grouping.decline_invitation(@student)\n+        expect(@grouping.pending?(@student)).to be false\n+      end\n+    end\n+\n+    context 'with a rejected membership' do\n+      before :each do\n+        @membership = create(:student_membership,\n+          grouping: @grouping,\n+          membership_status: StudentMembership::STATUSES[:rejected])\n+        @student = @membership.user\n+      end\n+\n+      it 'returns correct membership status' do\n+        expect(@grouping.membership_status(@student)).to eq('rejected')\n+      end\n+\n+      it 'is able to delete rejected memberships' do\n+        @grouping.remove_rejected(@membership.id)\n+        expect(@grouping.membership_status(@student)).to be_nil\n+      end\n+    end\n+\n+    context 'with TAs assigned' do\n+      ta_count = 3\n+      before :each do\n+        @tas = Array.new(ta_count) { create(:ta) }\n+        @grouping.add_tas(@tas)\n+      end\n+\n+      it 'has a ta for marking' do\n+        expect(@grouping.has_ta_for_marking?).to be true\n+      end\n+\n+      it 'gets ta names' do\n+        expect(@grouping.get_ta_names).to match_array(@tas.map(&:user_name))\n+      end\n+\n+      it 'is not be able to assign same TAs twice' do\n+        @grouping.reload\n+        expect(@grouping.ta_memberships.count).to eq(3)\n+        @grouping.add_tas(@tas)\n+        expect(@grouping.ta_memberships.count).to eq(3)\n+      end\n+\n+      it 'is able to remove ta' do\n+        @grouping.remove_tas(@tas)\n+        expect(@grouping.ta_memberships.count).to eq(0)\n+      end\n+    end\n+\n+    context 'with some submitted files' do\n+      # submit files\n+      before :each do\n+        @assignment = create(:assignment)\n+        @file = create(:assignment_file, assignment: @assignment)\n+        @grouping = create(:grouping, assignment: @assignment)\n+        @grouping.group.access_repo do |repo|\n+          txn = repo.get_transaction('markus')\n+          assignment_folder = File.join(@assignment.repository_folder, File::SEPARATOR)\n+          begin\n+            txn.add(File.join(assignment_folder,\n+                              'Shapes.java'),\n+                    'shapes content',\n+                    'text/plain')\n+            unless repo.commit(txn)\n+              raise 'Unable to setup test!'\n+            end\n+          rescue Exception => e\n+            raise 'Test setup failed: ' + e.message\n+          end\n+        end\n+      end\n+\n+      teardown do\n+        destroy_repos\n+      end\n+\n+      it 'reports that grouping is not deleteable' do\n+        create(:inviter_student_membership,\n+          grouping: @grouping,\n+          membership_status: StudentMembership::STATUSES[:inviter])\n+        create(:accepted_student_membership,\n+          grouping: @grouping,\n+          membership_status: StudentMembership::STATUSES[:accepted])\n+\n+        expect(@grouping.deletable_by?(@grouping.inviter)).to be false\n+      end\n+\n+      # FAILING: missing_file.length = 0\n+      it 'is able to report the still missing required assignment_files' do\n+        missing_files = @grouping.missing_assignment_files\n+        expect(missing_files.length).to eq(1)\n+        expect(missing_files).to eq([@file])\n+        # submit another file so that we have all required files submitted\n+        @grouping.group.access_repo do |repo|\n+          txn = repo.get_transaction('markus')\n+          begin\n+            txn.add(File.join(@assignment.repository_folder,\n+                              @file.filename),\n+                    'ShapesTest content',\n+                    'text/plain')\n+            unless repo.commit(txn)\n+              raise 'Commit failed!'\n+            end\n+          rescue Exception => e\n+            raise 'Submitting file failed: ' + e.message\n+          end\n+          # check again; there shouldn't be any missing files anymore\n+          missing_files = @grouping.missing_assignment_files\n+          expect(missing_files.length).to eq(0)\n+        end\n+      end\n+    end\n+\n+    context 'calling has_submission? with many submissions, all with submission_version_used == false' do\n+      before :each do\n+        @submission1 = create(:submission, submission_version_used: false,\n+                                       grouping: @grouping)\n+        @submission2 = create(:submission, submission_version_used: false,\n+                                       grouping: @grouping)\n+        @submission3 = create(:submission, submission_version_used: false,\n+                                       grouping: @grouping)\n+        @grouping.reload\n+      end\n+\n+      it 'behaves like theres no submission and return false' do\n+        #sort only to ensure same order of arrays\n+        expect(@grouping.submissions.sort{|a,b| a.id <=> b.id}).to match([@submission1, @submission2, @submission3]\n+                                                                           .sort{|a,b| a.id <=> b.id})\n+        expect(@grouping.current_submission_used).to be_nil\n+        expect(@grouping.has_submission?).to be false\n+      end\n+    end\n+\n+    #The order in which submissions are added to the grouping matters because\n+    #after a submission is created, it ensures that all other submissions have\n+    #submission_version_used set to false.\n+    context 'calling has_submission? with many submissions, with the last submission added to the grouping having submission_version_used == false' do\n+      before :each do\n+        @submission1 = create(:submission, submission_version_used: true, grouping: @grouping)\n+        @submission2 = create(:submission, submission_version_used: false, grouping: @grouping)\n+        @submission3 = create(:submission, submission_version_used: true, grouping: @grouping)\n+        @submission4 = create(:submission, submission_version_used: false, grouping: @grouping)\n+        @grouping.reload\n+      end\n+      it 'behaves like there is no submission' do\n+        #sort only to ensure same order of arrays\n+        expect(@grouping.submissions.sort{|a,b| a.id <=> b.id})\n+          .to match_array([@submission1, @submission2, @submission3, @submission4].sort{|a,b| a.id <=> b.id})\n+        expect(@grouping.current_submission_used).to be_nil\n+        expect(@grouping.has_submission?).to be false\n+      end\n+    end\n+\n+    context 'calling has_submission? with many submissions, with the last submission added to the grouping having submission_version_used == true' do\n+      before :each do\n+        @submission1 = create(:submission, submission_version_used: false, grouping: @grouping)\n+        @submission2 = create(:submission, submission_version_used: true, grouping: @grouping)\n+        @submission3 = create(:submission, submission_version_used: true, grouping: @grouping)\n+        @grouping.reload\n+      end\n+\n+      it 'behaves like there is a submission' do\n+        #sort only to ensure same order of arrays\n+        expect(@grouping.submissions.sort{|a,b| a.id <=> b.id}).\n+          to match_array([@submission1, @submission2, @submission3].sort{|a,b| a.id <=> b.id})\n+        expect(@submission2.reload.submission_version_used).to be false\n+        expect(@grouping.current_submission_used).to eq(@submission3)\n+        expect(@grouping.has_submission?).to be true\n+      end\n+    end\n+\n+    context 'containing multiple submissions with submission_version_used == true' do\n+      before :each do\n+        #Dont use machinist in order to bypass validation\n+        @submission1 = @grouping.submissions.build(submission_version_used: false,\n+                                                   revision_identifier: 1, revision_timestamp: 1.days.ago, submission_version: 1)\n+        @submission1.save(validate: false)\n+        @submission2 = @grouping.submissions.build(submission_version_used: true,\n+                                                   revision_identifier: 1, revision_timestamp: 1.days.ago, submission_version: 2)\n+        @submission2.save(validate: false)\n+        @submission3 = @grouping.submissions.build(submission_version_used: true,\n+                                                   revision_identifier: 1, revision_timestamp: 1.days.ago, submission_version: 3)\n+        @submission3.save(validate: false)\n+        @grouping.reload\n+      end\n+\n+      it \"sets all the submissions' submission_version_used columns to false upon creation of a new submission\" do\n+        #sort only to ensure same order of arrays\n+        expect(@grouping.submissions.sort{|a,b| a.id <=> b.id}).\n+          to eq([@submission1, @submission2, @submission3].sort{|a,b| a.id <=> b.id})\n+\n+        expect(@grouping.has_submission?).to be true\n+        #Make sure current_submission_used returns a single Submission, not an array\n+        expect(@grouping.current_submission_used.is_a?(Submission)).to be true\n+        @submission4 = create(:submission, submission_version_used: false, grouping: @grouping)\n+        @grouping.reload\n+        expect(@grouping.has_submission?).to be false\n+        expect(@submission4.submission_version).to eq(4)\n+        @submission5 = create(:submission, submission_version_used: true, grouping: @grouping)\n+        @grouping.reload\n+        expect(@grouping.has_submission?).to be true\n+        expect(@grouping.current_submission_used).to eq(@submission5)\n+      end\n+    end\n+\n+    context 'A grouping without students (ie created by an admin)' do\n+      before :each do\n+        @student_01 = create(:student)\n+        @student_02 = create(:student)\n+      end\n+\n+      it 'accepts to add students in any scenario possible when invoked by admin' do\n+        members = [@student_01.user_name, @student_02.user_name]\n+        @grouping.invite(members,\n+                         StudentMembership::STATUSES[:accepted],\n+                         true)\n+        expect(@grouping.accepted_student_memberships.count).to eq(2)\n+      end\n+    end\n+\n+    context 'A grouping without students (ie created by an admin) for a assignment with section restriction' do\n+      before :each do\n+        @assignment = create(:assignment, section_due_dates_type: true)\n+        @grouping = create(:grouping, assignment: @assignment)\n+        section_01 = create(:section)\n+        section_02 = create(:section)\n+        @student_01 = create(:student, section: section_01)\n+        @student_02 = create(:student, section: section_02)\n+      end\n+\n+      it 'accepts to add students to groups without checking their sections' do\n+        members = [@student_01.user_name, @student_02.user_name]\n+        @grouping.invite(members,\n+                         StudentMembership::STATUSES[:accepted],\n+                         true)\n+        expect(@grouping.accepted_student_memberships.count).to eq(2)\n+      end\n+    end\n+\n+    context 'A grouping with students in section' do\n+      before :each do\n+        @section = create(:section)\n+        student  = create(:student, section: @section)\n+        @student_can_invite = create(:student, section: @section)\n+        @student_cannot_invite = create(:student)\n+\n+        assignment = create(:assignment, section_groups_only: true)\n+        @grouping = create(:grouping, assignment: assignment)\n+        create(:inviter_student_membership, user: student, grouping: @grouping,\n+               membership_status: StudentMembership::STATUSES[:inviter])\n+      end\n+\n+      # FAILING: @grouping.can_invite?(@student_can_invite) returns false\n+      it 'returns true to can invite for students of same section' do\n+        expect(@grouping.can_invite?(@student_can_invite)).to be true\n+      end\n+\n+      it 'returns false to can invite for students of different section' do\n+        expect(@grouping.can_invite?(@student_cannot_invite)).to be false\n+      end\n+    end\n+\n+    context 'Assignment has a grace period of 24 hours after due date' do\n+      before :each do\n+        @assignment = create(:assignment)\n+        @group = create(:group)\n+        grace_period_submission_rule = GracePeriodSubmissionRule.new\n+        @assignment.replace_submission_rule(grace_period_submission_rule)\n+        GracePeriodDeduction.destroy_all\n+        grace_period_submission_rule.save\n+\n+        # On July 1 at 1PM, the instructor sets up the course...\n+        pretend_now_is(Time.parse('July 1 2009 1:00PM')) do\n+          # Due date is July 23 @ 5PM\n+          @assignment.due_date = Time.parse('July 23 2009 5:00PM')\n+          # Overtime begins at July 23 @ 5PM\n+          # Add a 24 hour grace period\n+          period = Period.new\n+          period.submission_rule = @assignment.submission_rule\n+          period.hours = 24\n+          period.save\n+          # Collect date is now after July 24 @ 5PM\n+          @assignment.save\n+        end\n+      end\n+\n+      teardown do\n+        destroy_repos\n+      end\n+\n+      context 'A grouping of one student submitting an assignment' do\n+        before :each do\n+          # grouping of only one student\n+          @grouping = create(:grouping, assignment: @assignment, group: @group)\n+          @inviter_membership = create(:inviter_student_membership, user: create(:student, user_name: 'student1'),\n+                                                       grouping: @grouping,\n+                                                       membership_status: StudentMembership::STATUSES[:inviter])\n+          @inviter = @inviter_membership.user\n+\n+          # On July 15, the Student logs in, triggering repository folder creation\n+          pretend_now_is(Time.parse('July 15 2009 6:00PM')) do\n+            @grouping.create_grouping_repository_folder\n+          end\n+        end\n+\n+        it 'does not deduct grace credits because submission is on time' do\n+\n+          # Check the number of member in this grouping\n+          expect(@grouping.student_membership_number).to eq(1)\n+\n+          submit_files_before_due_date\n+\n+          # An Instructor or Grader decides to begin grading\n+          pretend_now_is(Time.parse('July 28 2009 1:00PM')) do\n+            submission = Submission.create_by_timestamp(@grouping, @assignment.submission_rule.calculate_collection_time)\n+            submission = @assignment.submission_rule.apply_submission_rule(submission)\n+\n+            @grouping.reload\n+            # Should be no deduction because submitting on time\n+            expect(@grouping.grace_period_deduction_single).to eq(0)\n+          end\n+        end\n+\n+        it 'deducts one grace credit' do\n+\n+          # Check the number of member in this grouping\n+          expect(@grouping.student_membership_number).to eq(1)\n+          # Make sure the available grace credits are enough\n+          expect(@grouping.available_grace_credits).to be >= 1\n+\n+          submit_files_after_due_date('July 24 2009 9:00AM', 'LateSubmission.java', 'Some overtime contents')\n+\n+          # An Instructor or Grader decides to begin grading\n+          pretend_now_is(Time.parse('July 28 2009 1:00PM')) do\n+            submission = Submission.create_by_timestamp(@grouping, @assignment.submission_rule.calculate_collection_time)\n+            submission = @assignment.submission_rule.apply_submission_rule(submission)\n+\n+            @grouping.reload\n+            # Should display 1 credit deduction because of one-day late submission\n+            expect(@grouping.grace_period_deduction_single).to eq(1)\n+          end\n+        end\n+      end # end of context \"A grouping of one student submitting an assignment\"\n+\n+      context 'A grouping of two students submitting an assignment' do\n+        before :each do\n+          # grouping of two students\n+          @grouping = create(:grouping, assignment: @assignment, group: @group)\n+          # should consist of inviter and another student\n+          @membership = create(:accepted_student_membership, user: create(:student, user_name: 'student1'),\n+                                               grouping: @grouping,\n+                                               membership_status: StudentMembership::STATUSES[:accepted])\n+\n+          @inviter_membership = create(:inviter_student_membership, user: create(:student, user_name: 'student2'),\n+                                                       grouping: @grouping,\n+                                                       membership_status: StudentMembership::STATUSES[:inviter])\n+          @inviter = @inviter_membership.user\n+\n+          # On July 15, the Student logs in, triggering repository folder creation\n+          pretend_now_is(Time.parse('July 15 2009 6:00PM')) do\n+            @grouping.create_grouping_repository_folder\n+          end\n+        end\n+\n+        it 'does not deduct grace credits because submission is on time' do\n+\n+          # Check the number of member in this grouping\n+          expect(@grouping.student_membership_number).to eq(2)\n+\n+          submit_files_before_due_date\n+\n+          # An Instructor or Grader decides to begin grading\n+          pretend_now_is(Time.parse('July 28 2009 1:00PM')) do\n+            submission = Submission.create_by_timestamp(@grouping, @assignment.submission_rule.calculate_collection_time)\n+            submission = @assignment.submission_rule.apply_submission_rule(submission)\n+\n+            @grouping.reload\n+            # Should be no deduction because submitting on time\n+            expect(@grouping.grace_period_deduction_single).to eq(0)\n+          end\n+        end\n+\n+        it 'deducts one grace credit' do\n+\n+          # Check the number of member in this grouping\n+          expect(@grouping.student_membership_number).to eq(2)\n+          # Make sure the available grace credits are enough\n+          expect(@grouping.available_grace_credits).to be >= 1\n+\n+          submit_files_after_due_date('July 24 2009 9:00AM', 'LateSubmission.java', 'Some overtime contents')\n+\n+          # An Instructor or Grader decides to begin grading\n+          pretend_now_is(Time.parse('July 28 2009 1:00PM')) do\n+            submission = Submission.create_by_timestamp(@grouping, @assignment.submission_rule.calculate_collection_time)","path":"spec/models/grouping_spec.rb","position":476,"original_position":535,"commit_id":"47d87f53feb4543e5315629e564af3765be09dbf","original_commit_id":"47d87f53feb4543e5315629e564af3765be09dbf","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/LineLength: Line is too long. [121/120]","created_at":"2018-09-19T15:09:58Z","updated_at":"2018-09-19T15:10:00Z","html_url":"https://github.com/MarkUsProject/Markus/pull/3553#discussion_r218843916","pull_request_url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553","author_association":"NONE","_links":{"self":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/comments/218843916"},"html":{"href":"https://github.com/MarkUsProject/Markus/pull/3553#discussion_r218843916"},"pull_request":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553"}}},"pull_request":{"url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553","id":216675795,"node_id":"MDExOlB1bGxSZXF1ZXN0MjE2Njc1Nzk1","html_url":"https://github.com/MarkUsProject/Markus/pull/3553","diff_url":"https://github.com/MarkUsProject/Markus/pull/3553.diff","patch_url":"https://github.com/MarkUsProject/Markus/pull/3553.patch","issue_url":"https://api.github.com/repos/MarkUsProject/Markus/issues/3553","number":3553,"state":"open","locked":false,"title":"Unit to rspec tests","user":{"login":"hl197","id":19288961,"node_id":"MDQ6VXNlcjE5Mjg4OTYx","avatar_url":"https://avatars0.githubusercontent.com/u/19288961?v=4","gravatar_id":"","url":"https://api.github.com/users/hl197","html_url":"https://github.com/hl197","followers_url":"https://api.github.com/users/hl197/followers","following_url":"https://api.github.com/users/hl197/following{/other_user}","gists_url":"https://api.github.com/users/hl197/gists{/gist_id}","starred_url":"https://api.github.com/users/hl197/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/hl197/subscriptions","organizations_url":"https://api.github.com/users/hl197/orgs","repos_url":"https://api.github.com/users/hl197/repos","events_url":"https://api.github.com/users/hl197/events{/privacy}","received_events_url":"https://api.github.com/users/hl197/received_events","type":"User","site_admin":false},"body":"Converted tests from test/unit for assignment, flexible criterion, grace period submission rule, and grouping to rspec tests at spec/models.\r\nRemoved the old test files.\r\nNote: Assignment tests only partially converted. New failing rspec tests are marked with # FAILING.","created_at":"2018-09-19T15:09:39Z","updated_at":"2018-09-19T15:09:59Z","closed_at":null,"merged_at":null,"merge_commit_sha":"24237ac8cda45ce7e07a009fa8796e5231d90168","assignee":null,"assignees":[],"requested_reviewers":[],"requested_teams":[],"labels":[],"milestone":null,"commits_url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553/commits","review_comments_url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553/comments","review_comment_url":"https://api.github.com/repos/MarkUsProject/Markus/pulls/comments{/number}","comments_url":"https://api.github.com/repos/MarkUsProject/Markus/issues/3553/comments","statuses_url":"https://api.github.com/repos/MarkUsProject/Markus/statuses/47d87f53feb4543e5315629e564af3765be09dbf","head":{"label":"hl197:unit-to-rspec-tests","ref":"unit-to-rspec-tests","sha":"47d87f53feb4543e5315629e564af3765be09dbf","user":{"login":"hl197","id":19288961,"node_id":"MDQ6VXNlcjE5Mjg4OTYx","avatar_url":"https://avatars0.githubusercontent.com/u/19288961?v=4","gravatar_id":"","url":"https://api.github.com/users/hl197","html_url":"https://github.com/hl197","followers_url":"https://api.github.com/users/hl197/followers","following_url":"https://api.github.com/users/hl197/following{/other_user}","gists_url":"https://api.github.com/users/hl197/gists{/gist_id}","starred_url":"https://api.github.com/users/hl197/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/hl197/subscriptions","organizations_url":"https://api.github.com/users/hl197/orgs","repos_url":"https://api.github.com/users/hl197/repos","events_url":"https://api.github.com/users/hl197/events{/privacy}","received_events_url":"https://api.github.com/users/hl197/received_events","type":"User","site_admin":false},"repo":{"id":148238496,"node_id":"MDEwOlJlcG9zaXRvcnkxNDgyMzg0OTY=","name":"Markus","full_name":"hl197/Markus","private":false,"owner":{"login":"hl197","id":19288961,"node_id":"MDQ6VXNlcjE5Mjg4OTYx","avatar_url":"https://avatars0.githubusercontent.com/u/19288961?v=4","gravatar_id":"","url":"https://api.github.com/users/hl197","html_url":"https://github.com/hl197","followers_url":"https://api.github.com/users/hl197/followers","following_url":"https://api.github.com/users/hl197/following{/other_user}","gists_url":"https://api.github.com/users/hl197/gists{/gist_id}","starred_url":"https://api.github.com/users/hl197/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/hl197/subscriptions","organizations_url":"https://api.github.com/users/hl197/orgs","repos_url":"https://api.github.com/users/hl197/repos","events_url":"https://api.github.com/users/hl197/events{/privacy}","received_events_url":"https://api.github.com/users/hl197/received_events","type":"User","site_admin":false},"html_url":"https://github.com/hl197/Markus","description":"Git repository of MarkUs","fork":true,"url":"https://api.github.com/repos/hl197/Markus","forks_url":"https://api.github.com/repos/hl197/Markus/forks","keys_url":"https://api.github.com/repos/hl197/Markus/keys{/key_id}","collaborators_url":"https://api.github.com/repos/hl197/Markus/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/hl197/Markus/teams","hooks_url":"https://api.github.com/repos/hl197/Markus/hooks","issue_events_url":"https://api.github.com/repos/hl197/Markus/issues/events{/number}","events_url":"https://api.github.com/repos/hl197/Markus/events","assignees_url":"https://api.github.com/repos/hl197/Markus/assignees{/user}","branches_url":"https://api.github.com/repos/hl197/Markus/branches{/branch}","tags_url":"https://api.github.com/repos/hl197/Markus/tags","blobs_url":"https://api.github.com/repos/hl197/Markus/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/hl197/Markus/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/hl197/Markus/git/refs{/sha}","trees_url":"https://api.github.com/repos/hl197/Markus/git/trees{/sha}","statuses_url":"https://api.github.com/repos/hl197/Markus/statuses/{sha}","languages_url":"https://api.github.com/repos/hl197/Markus/languages","stargazers_url":"https://api.github.com/repos/hl197/Markus/stargazers","contributors_url":"https://api.github.com/repos/hl197/Markus/contributors","subscribers_url":"https://api.github.com/repos/hl197/Markus/subscribers","subscription_url":"https://api.github.com/repos/hl197/Markus/subscription","commits_url":"https://api.github.com/repos/hl197/Markus/commits{/sha}","git_commits_url":"https://api.github.com/repos/hl197/Markus/git/commits{/sha}","comments_url":"https://api.github.com/repos/hl197/Markus/comments{/number}","issue_comment_url":"https://api.github.com/repos/hl197/Markus/issues/comments{/number}","contents_url":"https://api.github.com/repos/hl197/Markus/contents/{+path}","compare_url":"https://api.github.com/repos/hl197/Markus/compare/{base}...{head}","merges_url":"https://api.github.com/repos/hl197/Markus/merges","archive_url":"https://api.github.com/repos/hl197/Markus/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/hl197/Markus/downloads","issues_url":"https://api.github.com/repos/hl197/Markus/issues{/number}","pulls_url":"https://api.github.com/repos/hl197/Markus/pulls{/number}","milestones_url":"https://api.github.com/repos/hl197/Markus/milestones{/number}","notifications_url":"https://api.github.com/repos/hl197/Markus/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/hl197/Markus/labels{/name}","releases_url":"https://api.github.com/repos/hl197/Markus/releases{/id}","deployments_url":"https://api.github.com/repos/hl197/Markus/deployments","created_at":"2018-09-11T00:49:15Z","updated_at":"2018-09-17T15:04:02Z","pushed_at":"2018-09-19T15:01:46Z","git_url":"git://github.com/hl197/Markus.git","ssh_url":"git@github.com:hl197/Markus.git","clone_url":"https://github.com/hl197/Markus.git","svn_url":"https://github.com/hl197/Markus","homepage":"http://www.markusproject.org","size":115498,"stargazers_count":0,"watchers_count":0,"language":"Ruby","has_issues":false,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"archived":false,"open_issues_count":0,"license":{"key":"mit","name":"MIT License","spdx_id":"MIT","url":"https://api.github.com/licenses/mit","node_id":"MDc6TGljZW5zZTEz"},"forks":0,"open_issues":0,"watchers":0,"default_branch":"master"}},"base":{"label":"MarkUsProject:master","ref":"master","sha":"c2dbff9478d1bc001bb2c762f814f2f27239fc78","user":{"login":"MarkUsProject","id":415874,"node_id":"MDEyOk9yZ2FuaXphdGlvbjQxNTg3NA==","avatar_url":"https://avatars1.githubusercontent.com/u/415874?v=4","gravatar_id":"","url":"https://api.github.com/users/MarkUsProject","html_url":"https://github.com/MarkUsProject","followers_url":"https://api.github.com/users/MarkUsProject/followers","following_url":"https://api.github.com/users/MarkUsProject/following{/other_user}","gists_url":"https://api.github.com/users/MarkUsProject/gists{/gist_id}","starred_url":"https://api.github.com/users/MarkUsProject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/MarkUsProject/subscriptions","organizations_url":"https://api.github.com/users/MarkUsProject/orgs","repos_url":"https://api.github.com/users/MarkUsProject/repos","events_url":"https://api.github.com/users/MarkUsProject/events{/privacy}","received_events_url":"https://api.github.com/users/MarkUsProject/received_events","type":"Organization","site_admin":false},"repo":{"id":940538,"node_id":"MDEwOlJlcG9zaXRvcnk5NDA1Mzg=","name":"Markus","full_name":"MarkUsProject/Markus","private":false,"owner":{"login":"MarkUsProject","id":415874,"node_id":"MDEyOk9yZ2FuaXphdGlvbjQxNTg3NA==","avatar_url":"https://avatars1.githubusercontent.com/u/415874?v=4","gravatar_id":"","url":"https://api.github.com/users/MarkUsProject","html_url":"https://github.com/MarkUsProject","followers_url":"https://api.github.com/users/MarkUsProject/followers","following_url":"https://api.github.com/users/MarkUsProject/following{/other_user}","gists_url":"https://api.github.com/users/MarkUsProject/gists{/gist_id}","starred_url":"https://api.github.com/users/MarkUsProject/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/MarkUsProject/subscriptions","organizations_url":"https://api.github.com/users/MarkUsProject/orgs","repos_url":"https://api.github.com/users/MarkUsProject/repos","events_url":"https://api.github.com/users/MarkUsProject/events{/privacy}","received_events_url":"https://api.github.com/users/MarkUsProject/received_events","type":"Organization","site_admin":false},"html_url":"https://github.com/MarkUsProject/Markus","description":"Git repository of MarkUs","fork":false,"url":"https://api.github.com/repos/MarkUsProject/Markus","forks_url":"https://api.github.com/repos/MarkUsProject/Markus/forks","keys_url":"https://api.github.com/repos/MarkUsProject/Markus/keys{/key_id}","collaborators_url":"https://api.github.com/repos/MarkUsProject/Markus/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/MarkUsProject/Markus/teams","hooks_url":"https://api.github.com/repos/MarkUsProject/Markus/hooks","issue_events_url":"https://api.github.com/repos/MarkUsProject/Markus/issues/events{/number}","events_url":"https://api.github.com/repos/MarkUsProject/Markus/events","assignees_url":"https://api.github.com/repos/MarkUsProject/Markus/assignees{/user}","branches_url":"https://api.github.com/repos/MarkUsProject/Markus/branches{/branch}","tags_url":"https://api.github.com/repos/MarkUsProject/Markus/tags","blobs_url":"https://api.github.com/repos/MarkUsProject/Markus/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/MarkUsProject/Markus/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/MarkUsProject/Markus/git/refs{/sha}","trees_url":"https://api.github.com/repos/MarkUsProject/Markus/git/trees{/sha}","statuses_url":"https://api.github.com/repos/MarkUsProject/Markus/statuses/{sha}","languages_url":"https://api.github.com/repos/MarkUsProject/Markus/languages","stargazers_url":"https://api.github.com/repos/MarkUsProject/Markus/stargazers","contributors_url":"https://api.github.com/repos/MarkUsProject/Markus/contributors","subscribers_url":"https://api.github.com/repos/MarkUsProject/Markus/subscribers","subscription_url":"https://api.github.com/repos/MarkUsProject/Markus/subscription","commits_url":"https://api.github.com/repos/MarkUsProject/Markus/commits{/sha}","git_commits_url":"https://api.github.com/repos/MarkUsProject/Markus/git/commits{/sha}","comments_url":"https://api.github.com/repos/MarkUsProject/Markus/comments{/number}","issue_comment_url":"https://api.github.com/repos/MarkUsProject/Markus/issues/comments{/number}","contents_url":"https://api.github.com/repos/MarkUsProject/Markus/contents/{+path}","compare_url":"https://api.github.com/repos/MarkUsProject/Markus/compare/{base}...{head}","merges_url":"https://api.github.com/repos/MarkUsProject/Markus/merges","archive_url":"https://api.github.com/repos/MarkUsProject/Markus/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/MarkUsProject/Markus/downloads","issues_url":"https://api.github.com/repos/MarkUsProject/Markus/issues{/number}","pulls_url":"https://api.github.com/repos/MarkUsProject/Markus/pulls{/number}","milestones_url":"https://api.github.com/repos/MarkUsProject/Markus/milestones{/number}","notifications_url":"https://api.github.com/repos/MarkUsProject/Markus/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/MarkUsProject/Markus/labels{/name}","releases_url":"https://api.github.com/repos/MarkUsProject/Markus/releases{/id}","deployments_url":"https://api.github.com/repos/MarkUsProject/Markus/deployments","created_at":"2010-09-26T16:18:08Z","updated_at":"2018-09-17T20:10:20Z","pushed_at":"2018-09-19T15:09:40Z","git_url":"git://github.com/MarkUsProject/Markus.git","ssh_url":"git@github.com:MarkUsProject/Markus.git","clone_url":"https://github.com/MarkUsProject/Markus.git","svn_url":"https://github.com/MarkUsProject/Markus","homepage":"http://www.markusproject.org","size":115686,"stargazers_count":176,"watchers_count":176,"language":"Ruby","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":194,"mirror_url":null,"archived":false,"open_issues_count":74,"license":{"key":"mit","name":"MIT License","spdx_id":"MIT","url":"https://api.github.com/licenses/mit","node_id":"MDc6TGljZW5zZTEz"},"forks":194,"open_issues":74,"watchers":176,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553"},"html":{"href":"https://github.com/MarkUsProject/Markus/pull/3553"},"issue":{"href":"https://api.github.com/repos/MarkUsProject/Markus/issues/3553"},"comments":{"href":"https://api.github.com/repos/MarkUsProject/Markus/issues/3553/comments"},"review_comments":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553/comments"},"review_comment":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/MarkUsProject/Markus/pulls/3553/commits"},"statuses":{"href":"https://api.github.com/repos/MarkUsProject/Markus/statuses/47d87f53feb4543e5315629e564af3765be09dbf"}},"author_association":"NONE"}}
{"actor":{"display_login":"houndci-bot"}}