summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlfredo Sumaran <alfredo@gitlab.com>2017-03-14 18:45:12 +0000
committerAlfredo Sumaran <alfredo@gitlab.com>2017-03-14 18:45:12 +0000
commit36bddc05a80ed1dee4a58f9428f52f7b055f5979 (patch)
tree1107e7a94461f70d2a77f4c93512dda22d81befe
parent39b1110727401bd7b97c012a3ee1cd2024c9f727 (diff)
parent35f3bed7865c49d9245d65ea81baef99113a9819 (diff)
downloadgitlab-ce-20450-fix-ujs-actions-part-3-step4.tar.gz
Merge branch '20450-fix-ujs-actions-part-3-step5' into '20450-fix-ujs-actions-part-3-step4' 20450-fix-ujs-actions-part-3-step4
Resolve "Opening Retry build button on merge requests page in new tab / window doesn't work" See merge request !9869
-rw-r--r--app/assets/javascripts/commit/pipelines/pipelines_service.js40
-rw-r--r--app/assets/javascripts/commit/pipelines/pipelines_store.js46
-rw-r--r--app/assets/javascripts/commit/pipelines/pipelines_table.js10
-rw-r--r--app/assets/javascripts/vue_pipelines_index/pipelines.js3
-rw-r--r--app/assets/javascripts/vue_pipelines_index/stores/pipelines_store.js31
-rw-r--r--spec/javascripts/commit/pipelines/mock_data.js5
-rw-r--r--spec/javascripts/commit/pipelines/pipelines_spec.js26
-rw-r--r--spec/javascripts/commit/pipelines/pipelines_store_spec.js33
-rw-r--r--spec/javascripts/vue_pipelines_index/pipeline_url_spec.js100
-rw-r--r--spec/javascripts/vue_shared/components/commit_spec.js27
-rw-r--r--spec/javascripts/vue_shared/components/pipelines_table_row_spec.js12
-rw-r--r--spec/javascripts/vue_shared/components/pipelines_table_spec.js25
12 files changed, 181 insertions, 177 deletions
diff --git a/app/assets/javascripts/commit/pipelines/pipelines_service.js b/app/assets/javascripts/commit/pipelines/pipelines_service.js
deleted file mode 100644
index 40fabd90a9e..00000000000
--- a/app/assets/javascripts/commit/pipelines/pipelines_service.js
+++ /dev/null
@@ -1,40 +0,0 @@
-import Vue from 'vue';
-import VueResource from 'vue-resource';
-
-Vue.use(VueResource);
-/**
- * Pipelines service.
- *
- * Used to fetch the data used to render the pipelines table.
- * Uses Vue.Resource
- */
-export default class PipelinesService {
-
- /**
- * FIXME: The url provided to request the pipelines in the new merge request
- * page already has `.json`.
- * This should be fixed when the endpoint is improved.
- *
- * @param {String} root
- */
- constructor(root) {
- let endpoint;
-
- if (root.indexOf('.json') === -1) {
- endpoint = `${root}.json`;
- } else {
- endpoint = root;
- }
- this.pipelines = Vue.resource(endpoint);
- }
-
- /**
- * Given the root param provided when the class is initialized, will
- * make a GET request.
- *
- * @return {Promise}
- */
- all() {
- return this.pipelines.get();
- }
-}
diff --git a/app/assets/javascripts/commit/pipelines/pipelines_store.js b/app/assets/javascripts/commit/pipelines/pipelines_store.js
deleted file mode 100644
index 81413ff9aed..00000000000
--- a/app/assets/javascripts/commit/pipelines/pipelines_store.js
+++ /dev/null
@@ -1,46 +0,0 @@
-/* eslint-disable no-underscore-dangle*/
-/**
- * Pipelines' Store for commits view.
- *
- * Used to store the Pipelines rendered in the commit view in the pipelines table.
- */
-import '../../vue_realtime_listener';
-
-export default class PipelinesStore {
- constructor() {
- this.state = {};
- this.state.pipelines = [];
- }
-
- storePipelines(pipelines = []) {
- this.state.pipelines = pipelines;
-
- return pipelines;
- }
-
- /**
- * Once the data is received we will start the time ago loops.
- *
- * Everytime a request is made like retry or cancel a pipeline, every 10 seconds we
- * update the time to show how long as passed.
- *
- */
- static startTimeAgoLoops() {
- const startTimeLoops = () => {
- this.timeLoopInterval = setInterval(() => {
- this.$children[0].$children.reduce((acc, component) => {
- const timeAgoComponent = component.$children.filter(el => el.$options._componentTag === 'time-ago')[0];
- acc.push(timeAgoComponent);
- return acc;
- }, []).forEach(e => e.changeTime());
- }, 10000);
- };
-
- startTimeLoops();
-
- const removeIntervals = () => clearInterval(this.timeLoopInterval);
- const startIntervals = () => startTimeLoops();
-
- gl.VueRealtimeListener(removeIntervals, startIntervals);
- }
-}
diff --git a/app/assets/javascripts/commit/pipelines/pipelines_table.js b/app/assets/javascripts/commit/pipelines/pipelines_table.js
index 70448e817de..832c4b1bd2a 100644
--- a/app/assets/javascripts/commit/pipelines/pipelines_table.js
+++ b/app/assets/javascripts/commit/pipelines/pipelines_table.js
@@ -2,11 +2,11 @@
/* global Flash */
import Vue from 'vue';
import PipelinesTableComponent from '../../vue_shared/components/pipelines_table';
-import PipelinesService from './pipelines_service';
-import PipelineStore from './pipelines_store';
+import PipelinesService from '../../vue_pipelines_index/services/pipelines_service';
+import PipelineStore from '../../vue_pipelines_index/stores/pipelines_store';
+import eventHub from '../../vue_pipelines_index/event_hub';
import '../../lib/utils/common_utils';
import '../../vue_shared/vue_resource_interceptor';
-import eventHub from '../../vue_pipelines_index/event_hub';
/**
*
@@ -60,7 +60,7 @@ export default Vue.component('pipelines-table', {
beforeUpdate() {
if (this.state.pipelines.length && this.$children) {
- PipelineStore.startTimeAgoLoops.call(this, Vue);
+ this.store.startTimeAgoLoops.call(this, Vue);
}
},
@@ -71,7 +71,7 @@ export default Vue.component('pipelines-table', {
methods: {
fetchPipelines() {
this.isLoading = true;
- return this.service.all()
+ return this.service.getPipelines()
.then(response => response.json())
.then((json) => {
// depending of the endpoint the response can either bring a `pipelines` key or not.
diff --git a/app/assets/javascripts/vue_pipelines_index/pipelines.js b/app/assets/javascripts/vue_pipelines_index/pipelines.js
index 8b8ef60ec00..f389e5e4950 100644
--- a/app/assets/javascripts/vue_pipelines_index/pipelines.js
+++ b/app/assets/javascripts/vue_pipelines_index/pipelines.js
@@ -2,7 +2,6 @@
/* eslint-disable no-new */
import '~/flash';
import Vue from 'vue';
-import CommitPipelinesStoreWithTimeAgo from '../commit/pipelines/pipelines_store';
import PipelinesService from './services/pipelines_service';
import eventHub from './event_hub';
import PipelinesTableComponent from '../vue_shared/components/pipelines_table';
@@ -45,7 +44,7 @@ export default {
beforeUpdate() {
if (this.state.pipelines.length && this.$children) {
- CommitPipelinesStoreWithTimeAgo.startTimeAgoLoops.call(this, Vue);
+ this.store.startTimeAgoLoops.call(this, Vue);
}
},
diff --git a/app/assets/javascripts/vue_pipelines_index/stores/pipelines_store.js b/app/assets/javascripts/vue_pipelines_index/stores/pipelines_store.js
index ffefe0192f2..7ac10086a55 100644
--- a/app/assets/javascripts/vue_pipelines_index/stores/pipelines_store.js
+++ b/app/assets/javascripts/vue_pipelines_index/stores/pipelines_store.js
@@ -1,3 +1,6 @@
+/* eslint-disable no-underscore-dangle*/
+import '../../vue_realtime_listener';
+
export default class PipelinesStore {
constructor() {
this.state = {};
@@ -27,4 +30,32 @@ export default class PipelinesStore {
this.state.pageInfo = paginationInfo;
}
+
+ /**
+ * FIXME: Move this inside the component.
+ *
+ * Once the data is received we will start the time ago loops.
+ *
+ * Everytime a request is made like retry or cancel a pipeline, every 10 seconds we
+ * update the time to show how long as passed.
+ *
+ */
+ startTimeAgoLoops() {
+ const startTimeLoops = () => {
+ this.timeLoopInterval = setInterval(() => {
+ this.$children[0].$children.reduce((acc, component) => {
+ const timeAgoComponent = component.$children.filter(el => el.$options._componentTag === 'time-ago')[0];
+ acc.push(timeAgoComponent);
+ return acc;
+ }, []).forEach(e => e.changeTime());
+ }, 10000);
+ };
+
+ startTimeLoops();
+
+ const removeIntervals = () => clearInterval(this.timeLoopInterval);
+ const startIntervals = () => startTimeLoops();
+
+ gl.VueRealtimeListener(removeIntervals, startIntervals);
+ }
}
diff --git a/spec/javascripts/commit/pipelines/mock_data.js b/spec/javascripts/commit/pipelines/mock_data.js
index 188908d66bd..82b00b4c1ec 100644
--- a/spec/javascripts/commit/pipelines/mock_data.js
+++ b/spec/javascripts/commit/pipelines/mock_data.js
@@ -1,5 +1,4 @@
-/* eslint-disable no-unused-vars */
-const pipeline = {
+export default {
id: 73,
user: {
name: 'Administrator',
@@ -88,5 +87,3 @@ const pipeline = {
created_at: '2017-01-16T17:13:59.800Z',
updated_at: '2017-01-25T00:00:17.132Z',
};
-
-module.exports = pipeline;
diff --git a/spec/javascripts/commit/pipelines/pipelines_spec.js b/spec/javascripts/commit/pipelines/pipelines_spec.js
index f09c57978a1..60def442f34 100644
--- a/spec/javascripts/commit/pipelines/pipelines_spec.js
+++ b/spec/javascripts/commit/pipelines/pipelines_spec.js
@@ -1,17 +1,15 @@
-/* global pipeline, Vue */
-
-require('~/flash');
-require('~/commit/pipelines/pipelines_store');
-require('~/commit/pipelines/pipelines_service');
-require('~/commit/pipelines/pipelines_table');
-require('~/vue_shared/vue_resource_interceptor');
-const pipeline = require('./mock_data');
+import Vue from 'vue';
+import PipelinesTableComp from '~/commit/pipelines/pipelines_table';
+import pipeline from './mock_data';
describe('Pipelines table in Commits and Merge requests', () => {
+ let PipelinesTableView;
+
preloadFixtures('static/pipelines_table.html.raw');
beforeEach(() => {
loadFixtures('static/pipelines_table.html.raw');
+ PipelinesTableView = Vue.extend(PipelinesTableComp);
});
describe('successfull request', () => {
@@ -33,9 +31,9 @@ describe('Pipelines table in Commits and Merge requests', () => {
});
it('should render the empty state', (done) => {
- const component = new gl.commits.pipelines.PipelinesTableView({
+ const component = new PipelinesTableView({
el: document.querySelector('#commit-pipeline-table-view'),
- });
+ }).$mount();
setTimeout(() => {
expect(component.$el.querySelector('.js-blank-state-title').textContent).toContain('No pipelines to show');
@@ -62,9 +60,9 @@ describe('Pipelines table in Commits and Merge requests', () => {
});
it('should render a table with the received pipelines', (done) => {
- const component = new gl.commits.pipelines.PipelinesTableView({
+ const component = new PipelinesTableView({
el: document.querySelector('#commit-pipeline-table-view'),
- });
+ }).$mount();
setTimeout(() => {
expect(component.$el.querySelectorAll('table > tbody > tr').length).toEqual(1);
@@ -92,9 +90,9 @@ describe('Pipelines table in Commits and Merge requests', () => {
});
it('should render empty state', (done) => {
- const component = new gl.commits.pipelines.PipelinesTableView({
+ const component = new PipelinesTableView({
el: document.querySelector('#commit-pipeline-table-view'),
- });
+ }).$mount();
setTimeout(() => {
expect(component.$el.querySelector('.js-blank-state-title').textContent).toContain('No pipelines to show');
diff --git a/spec/javascripts/commit/pipelines/pipelines_store_spec.js b/spec/javascripts/commit/pipelines/pipelines_store_spec.js
deleted file mode 100644
index 94973419979..00000000000
--- a/spec/javascripts/commit/pipelines/pipelines_store_spec.js
+++ /dev/null
@@ -1,33 +0,0 @@
-const PipelinesStore = require('~/commit/pipelines/pipelines_store');
-
-describe('Store', () => {
- let store;
-
- beforeEach(() => {
- store = new PipelinesStore();
- });
-
- // unregister intervals and event handlers
- afterEach(() => gl.VueRealtimeListener.reset());
-
- it('should start with a blank state', () => {
- expect(store.state.pipelines.length).toBe(0);
- });
-
- it('should store an array of pipelines', () => {
- const pipelines = [
- {
- id: '1',
- name: 'pipeline',
- },
- {
- id: '2',
- name: 'pipeline_2',
- },
- ];
-
- store.storePipelines(pipelines);
-
- expect(store.state.pipelines.length).toBe(pipelines.length);
- });
-});
diff --git a/spec/javascripts/vue_pipelines_index/pipeline_url_spec.js b/spec/javascripts/vue_pipelines_index/pipeline_url_spec.js
new file mode 100644
index 00000000000..96a2a37b5f7
--- /dev/null
+++ b/spec/javascripts/vue_pipelines_index/pipeline_url_spec.js
@@ -0,0 +1,100 @@
+import Vue from 'vue';
+import pipelineUrlComp from '~/vue_pipelines_index/components/pipeline_url';
+
+describe('Pipeline Url Component', () => {
+ let PipelineUrlComponent;
+
+ beforeEach(() => {
+ PipelineUrlComponent = Vue.extend(pipelineUrlComp);
+ });
+
+ it('should render a table cell', () => {
+ const component = new PipelineUrlComponent({
+ propsData: {
+ pipeline: {
+ id: 1,
+ path: 'foo',
+ flags: {},
+ },
+ },
+ }).$mount();
+
+ expect(component.$el.tagName).toEqual('TD');
+ });
+
+ it('should render a link the provided path and id', () => {
+ const component = new PipelineUrlComponent({
+ propsData: {
+ pipeline: {
+ id: 1,
+ path: 'foo',
+ flags: {},
+ },
+ },
+ }).$mount();
+
+ expect(component.$el.querySelector('.js-pipeline-url-link').getAttribute('href')).toEqual('foo');
+ expect(component.$el.querySelector('.js-pipeline-url-link span').textContent).toEqual('#1');
+ });
+
+ it('should render user information when a user is provided', () => {
+ const mockData = {
+ pipeline: {
+ id: 1,
+ path: 'foo',
+ flags: {},
+ user: {
+ web_url: '/',
+ name: 'foo',
+ avatar_url: '/',
+ },
+ },
+ };
+
+ const component = new PipelineUrlComponent({
+ propsData: mockData,
+ }).$mount();
+
+ const image = component.$el.querySelector('.js-pipeline-url-user img');
+
+ expect(
+ component.$el.querySelector('.js-pipeline-url-user').getAttribute('href'),
+ ).toEqual(mockData.pipeline.user.web_url);
+ expect(image.getAttribute('title')).toEqual(mockData.pipeline.user.name);
+ expect(image.getAttribute('src')).toEqual(mockData.pipeline.user.avatar_url);
+ });
+
+ it('should render "API" when no user is provided', () => {
+ const component = new PipelineUrlComponent({
+ propsData: {
+ pipeline: {
+ id: 1,
+ path: 'foo',
+ flags: {},
+ },
+ },
+ }).$mount();
+
+ expect(component.$el.querySelector('.js-pipeline-url-api').textContent).toContain('API');
+ });
+
+ it('should render latest, yaml invalid and stuck flags when provided', () => {
+ const component = new PipelineUrlComponent({
+ propsData: {
+ pipeline: {
+ id: 1,
+ path: 'foo',
+ flags: {
+ latest: true,
+ yaml_errors: true,
+ stuck: true,
+ },
+ },
+ },
+ }).$mount();
+
+ expect(component.$el.querySelector('.js-pipeline-url-lastest').textContent).toContain('latest');
+ expect(component.$el.querySelector('.js-pipeline-url-yaml').textContent).toContain('yaml invalid');
+ expect(component.$el.querySelector('.js-pipeline-url-stuck').textContent).toContain('stuck');
+ });
+});
diff --git a/spec/javascripts/vue_shared/components/commit_spec.js b/spec/javascripts/vue_shared/components/commit_spec.js
index 15ab10b9b69..df547299d75 100644
--- a/spec/javascripts/vue_shared/components/commit_spec.js
+++ b/spec/javascripts/vue_shared/components/commit_spec.js
@@ -1,13 +1,17 @@
-require('~/vue_shared/components/commit');
+import Vue from 'vue';
+import commitComp from '~/vue_shared/components/commit';
describe('Commit component', () => {
let props;
let component;
+ let CommitComponent;
+
+ beforeEach(() => {
+ CommitComponent = Vue.extend(commitComp);
+ });
it('should render a code-fork icon if it does not represent a tag', () => {
- setFixtures('<div class="test-commit-container"></div>');
- component = new window.gl.CommitComponent({
- el: document.querySelector('.test-commit-container'),
+ component = new CommitComponent({
propsData: {
tag: false,
commitRef: {
@@ -23,15 +27,13 @@ describe('Commit component', () => {
username: 'jschatz1',
},
},
- });
+ }).$mount();
expect(component.$el.querySelector('.icon-container i').classList).toContain('fa-code-fork');
});
describe('Given all the props', () => {
beforeEach(() => {
- setFixtures('<div class="test-commit-container"></div>');
-
props = {
tag: true,
commitRef: {
@@ -49,10 +51,9 @@ describe('Commit component', () => {
commitIconSvg: '<svg></svg>',
};
- component = new window.gl.CommitComponent({
- el: document.querySelector('.test-commit-container'),
+ component = new CommitComponent({
propsData: props,
- });
+ }).$mount();
});
it('should render a tag icon if it represents a tag', () => {
@@ -105,7 +106,6 @@ describe('Commit component', () => {
describe('When commit title is not provided', () => {
it('should render default message', () => {
- setFixtures('<div class="test-commit-container"></div>');
props = {
tag: false,
commitRef: {
@@ -118,10 +118,9 @@ describe('Commit component', () => {
author: {},
};
- component = new window.gl.CommitComponent({
- el: document.querySelector('.test-commit-container'),
+ component = new CommitComponent({
propsData: props,
- });
+ }).$mount();
expect(
component.$el.querySelector('.commit-title span').textContent,
diff --git a/spec/javascripts/vue_shared/components/pipelines_table_row_spec.js b/spec/javascripts/vue_shared/components/pipelines_table_row_spec.js
index d24ec8a1aa1..699625cdbb7 100644
--- a/spec/javascripts/vue_shared/components/pipelines_table_row_spec.js
+++ b/spec/javascripts/vue_shared/components/pipelines_table_row_spec.js
@@ -1,20 +1,20 @@
-require('~/vue_shared/components/pipelines_table_row');
-const pipeline = require('../../commit/pipelines/mock_data');
+import Vue from 'vue';
+import tableRowComp from '~/vue_shared/components/pipelines_table_row';
+import pipeline from '../../commit/pipelines/mock_data';
describe('Pipelines Table Row', () => {
let component;
- preloadFixtures('static/environments/element.html.raw');
beforeEach(() => {
- loadFixtures('static/environments/element.html.raw');
+ const PipelinesTableRowComponent = Vue.extend(tableRowComp);
- component = new gl.pipelines.PipelinesTableRowComponent({
+ component = new PipelinesTableRowComponent({
el: document.querySelector('.test-dom-element'),
propsData: {
pipeline,
service: {},
},
- });
+ }).$mount();
});
it('should render a table row', () => {
diff --git a/spec/javascripts/vue_shared/components/pipelines_table_spec.js b/spec/javascripts/vue_shared/components/pipelines_table_spec.js
index 7abeb31b8fe..b0b1df5a753 100644
--- a/spec/javascripts/vue_shared/components/pipelines_table_spec.js
+++ b/spec/javascripts/vue_shared/components/pipelines_table_spec.js
@@ -1,24 +1,24 @@
-require('~/vue_shared/components/pipelines_table');
-require('~/lib/utils/datetime_utility');
-const pipeline = require('../../commit/pipelines/mock_data');
+import Vue from 'vue';
+import pipelinesTableComp from '~/vue_shared/components/pipelines_table';
+import '~/lib/utils/datetime_utility';
+import pipeline from '../../commit/pipelines/mock_data';
describe('Pipelines Table', () => {
- preloadFixtures('static/environments/element.html.raw');
+ let PipelinesTableComponent;
beforeEach(() => {
- loadFixtures('static/environments/element.html.raw');
+ PipelinesTableComponent = Vue.extend(pipelinesTableComp);
});
describe('table', () => {
let component;
beforeEach(() => {
- component = new gl.pipelines.PipelinesTableComponent({
- el: document.querySelector('.test-dom-element'),
+ component = new PipelinesTableComponent({
propsData: {
pipelines: [],
service: {},
},
- });
+ }).$mount();
});
it('should render a table', () => {
@@ -37,26 +37,25 @@ describe('Pipelines Table', () => {
describe('without data', () => {
it('should render an empty table', () => {
- const component = new gl.pipelines.PipelinesTableComponent({
- el: document.querySelector('.test-dom-element'),
+ const component = new PipelinesTableComponent({
propsData: {
pipelines: [],
service: {},
},
- });
+ }).$mount();
expect(component.$el.querySelectorAll('tbody tr').length).toEqual(0);
});
});
describe('with data', () => {
it('should render rows', () => {
- const component = new gl.pipelines.PipelinesTableComponent({
+ const component = new PipelinesTableComponent({
el: document.querySelector('.test-dom-element'),
propsData: {
pipelines: [pipeline],
service: {},
},
- });
+ }).$mount();
expect(component.$el.querySelectorAll('tbody tr').length).toEqual(1);
});