192 lines
		
	
	
		
			6.4 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
			
		
		
	
	
			192 lines
		
	
	
		
			6.4 KiB
		
	
	
	
		
			JavaScript
		
	
	
	
| /* eslint-disable space-before-function-paren, one-var, one-var-declaration-per-line, no-use-before-define, comma-dangle, max-len */
 | |
| import Issue from '~/issue';
 | |
| import '~/lib/utils/text_utility';
 | |
| 
 | |
| describe('Issue', function() {
 | |
|   let $boxClosed, $boxOpen, $btn;
 | |
| 
 | |
|   preloadFixtures('issues/closed-issue.html.raw');
 | |
|   preloadFixtures('issues/issue-with-task-list.html.raw');
 | |
|   preloadFixtures('issues/open-issue.html.raw');
 | |
| 
 | |
|   function expectErrorMessage() {
 | |
|     const $flashMessage = $('div.flash-alert');
 | |
|     expect($flashMessage).toExist();
 | |
|     expect($flashMessage).toBeVisible();
 | |
|     expect($flashMessage).toHaveText('Unable to update this issue at this time.');
 | |
|   }
 | |
| 
 | |
|   function expectIssueState(isIssueOpen) {
 | |
|     expectVisibility($boxClosed, !isIssueOpen);
 | |
|     expectVisibility($boxOpen, isIssueOpen);
 | |
|     expect($btn).toHaveText(isIssueOpen ? 'Close issue' : 'Reopen issue');
 | |
|   }
 | |
| 
 | |
|   function expectNewBranchButtonState(isPending, canCreate) {
 | |
|     if (Issue.$btnNewBranch.length === 0) {
 | |
|       return;
 | |
|     }
 | |
| 
 | |
|     const $available = Issue.$btnNewBranch.find('.available');
 | |
|     expect($available).toHaveText('New branch');
 | |
| 
 | |
|     if (!isPending && canCreate) {
 | |
|       expect($available).toBeVisible();
 | |
|     } else {
 | |
|       expect($available).toBeHidden();
 | |
|     }
 | |
| 
 | |
|     const $unavailable = Issue.$btnNewBranch.find('.unavailable');
 | |
|     expect($unavailable).toHaveText('New branch unavailable');
 | |
| 
 | |
|     if (!isPending && !canCreate) {
 | |
|       expect($unavailable).toBeVisible();
 | |
|     } else {
 | |
|       expect($unavailable).toBeHidden();
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   function expectVisibility($element, shouldBeVisible) {
 | |
|     if (shouldBeVisible) {
 | |
|       expect($element).not.toHaveClass('hidden');
 | |
|     } else {
 | |
|       expect($element).toHaveClass('hidden');
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   function findElements(isIssueInitiallyOpen) {
 | |
|     $boxClosed = $('div.status-box-issue-closed');
 | |
|     expect($boxClosed).toExist();
 | |
|     expect($boxClosed).toHaveText('Closed');
 | |
| 
 | |
|     $boxOpen = $('div.status-box-open');
 | |
|     expect($boxOpen).toExist();
 | |
|     expect($boxOpen).toHaveText('Open');
 | |
| 
 | |
|     $btn = $('.js-issuable-close-button');
 | |
|     expect($btn).toExist();
 | |
|     expect($btn).toHaveText(isIssueInitiallyOpen ? 'Close issue' : 'Reopen issue');
 | |
|   }
 | |
| 
 | |
|   describe('task lists', function() {
 | |
|     beforeEach(function() {
 | |
|       loadFixtures('issues/issue-with-task-list.html.raw');
 | |
|       this.issue = new Issue();
 | |
|     });
 | |
| 
 | |
|     it('submits an ajax request on tasklist:changed', function() {
 | |
|       spyOn(jQuery, 'ajax').and.callFake(function(req) {
 | |
|         expect(req.type).toBe('PATCH');
 | |
|         expect(req.url).toBe(gl.TEST_HOST + '/frontend-fixtures/issues-project/issues/1.json'); // eslint-disable-line prefer-template
 | |
|         expect(req.data.issue.description).not.toBe(null);
 | |
|       });
 | |
| 
 | |
|       $('.js-task-list-field').trigger('tasklist:changed');
 | |
|     });
 | |
|   });
 | |
| 
 | |
|   [true, false].forEach((isIssueInitiallyOpen) => {
 | |
|     describe(`with ${isIssueInitiallyOpen ? 'open' : 'closed'} issue`, function() {
 | |
|       const action = isIssueInitiallyOpen ? 'close' : 'reopen';
 | |
| 
 | |
|       function ajaxSpy(req) {
 | |
|         if (req.url === this.$triggeredButton.attr('href')) {
 | |
|           expect(req.type).toBe('PUT');
 | |
|           expectNewBranchButtonState(true, false);
 | |
|           return this.issueStateDeferred;
 | |
|         } else if (req.url === Issue.createMrDropdownWrap.dataset.canCreatePath) {
 | |
|           expect(req.type).toBe('GET');
 | |
|           expectNewBranchButtonState(true, false);
 | |
|           return this.canCreateBranchDeferred;
 | |
|         }
 | |
| 
 | |
|         expect(req.url).toBe('unexpected');
 | |
|         return null;
 | |
|       }
 | |
| 
 | |
|       beforeEach(function() {
 | |
|         if (isIssueInitiallyOpen) {
 | |
|           loadFixtures('issues/open-issue.html.raw');
 | |
|         } else {
 | |
|           loadFixtures('issues/closed-issue.html.raw');
 | |
|         }
 | |
| 
 | |
|         findElements(isIssueInitiallyOpen);
 | |
|         this.issue = new Issue();
 | |
|         expectIssueState(isIssueInitiallyOpen);
 | |
| 
 | |
|         this.$triggeredButton = $btn;
 | |
| 
 | |
|         this.$projectIssuesCounter = $('.issue_counter').first();
 | |
|         this.$projectIssuesCounter.text('1,001');
 | |
| 
 | |
|         this.issueStateDeferred = new jQuery.Deferred();
 | |
|         this.canCreateBranchDeferred = new jQuery.Deferred();
 | |
| 
 | |
|         spyOn(jQuery, 'ajax').and.callFake(ajaxSpy.bind(this));
 | |
|       });
 | |
| 
 | |
|       it(`${action}s the issue`, function() {
 | |
|         this.$triggeredButton.trigger('click');
 | |
|         this.issueStateDeferred.resolve({
 | |
|           id: 34
 | |
|         });
 | |
|         this.canCreateBranchDeferred.resolve({
 | |
|           can_create_branch: !isIssueInitiallyOpen
 | |
|         });
 | |
| 
 | |
|         expectIssueState(!isIssueInitiallyOpen);
 | |
|         expect(this.$triggeredButton.get(0).getAttribute('disabled')).toBeNull();
 | |
|         expect(this.$projectIssuesCounter.text()).toBe(isIssueInitiallyOpen ? '1,000' : '1,002');
 | |
|         expectNewBranchButtonState(false, !isIssueInitiallyOpen);
 | |
|       });
 | |
| 
 | |
|       it(`fails to ${action} the issue if saved:false`, function() {
 | |
|         this.$triggeredButton.trigger('click');
 | |
|         this.issueStateDeferred.resolve({
 | |
|           saved: false
 | |
|         });
 | |
|         this.canCreateBranchDeferred.resolve({
 | |
|           can_create_branch: isIssueInitiallyOpen
 | |
|         });
 | |
| 
 | |
|         expectIssueState(isIssueInitiallyOpen);
 | |
|         expect(this.$triggeredButton.get(0).getAttribute('disabled')).toBeNull();
 | |
|         expectErrorMessage();
 | |
|         expect(this.$projectIssuesCounter.text()).toBe('1,001');
 | |
|         expectNewBranchButtonState(false, isIssueInitiallyOpen);
 | |
|       });
 | |
| 
 | |
|       it(`fails to ${action} the issue if HTTP error occurs`, function() {
 | |
|         this.$triggeredButton.trigger('click');
 | |
|         this.issueStateDeferred.reject();
 | |
|         this.canCreateBranchDeferred.resolve({
 | |
|           can_create_branch: isIssueInitiallyOpen
 | |
|         });
 | |
| 
 | |
|         expectIssueState(isIssueInitiallyOpen);
 | |
|         expect(this.$triggeredButton.get(0).getAttribute('disabled')).toBeNull();
 | |
|         expectErrorMessage();
 | |
|         expect(this.$projectIssuesCounter.text()).toBe('1,001');
 | |
|         expectNewBranchButtonState(false, isIssueInitiallyOpen);
 | |
|       });
 | |
| 
 | |
|       it('disables the new branch button if Ajax call fails', function() {
 | |
|         this.$triggeredButton.trigger('click');
 | |
|         this.issueStateDeferred.reject();
 | |
|         this.canCreateBranchDeferred.reject();
 | |
| 
 | |
|         expectNewBranchButtonState(false, false);
 | |
|       });
 | |
| 
 | |
|       it('does not trigger Ajax call if new branch button is missing', function() {
 | |
|         Issue.$btnNewBranch = $();
 | |
|         this.canCreateBranchDeferred = null;
 | |
| 
 | |
|         this.$triggeredButton.trigger('click');
 | |
|         this.issueStateDeferred.reject();
 | |
|       });
 | |
|     });
 | |
|   });
 | |
| });
 |