diff --git a/.gitignore b/.gitignore index b8cbfe9966d..231541a2237 100644 --- a/.gitignore +++ b/.gitignore @@ -66,7 +66,7 @@ eslint-report.html /vendor/gitaly-ruby /builds* /.gitlab_workhorse_secret -/.gitlab_pages_shared_secret +/.gitlab_pages_secret /webpack-report/ /knapsack/ /rspec_flaky/ diff --git a/app/models/concerns/issuable.rb b/app/models/concerns/issuable.rb index 205bf4a5a26..bcb86a33138 100644 --- a/app/models/concerns/issuable.rb +++ b/app/models/concerns/issuable.rb @@ -148,26 +148,6 @@ module Issuable strip_attributes :title - # The state_machine gem will reset the value of state_id unless it - # is a raw attribute passed in here: - # https://gitlab.com/gitlab-org/gitlab/issues/35746#note_241148787 - # - # This assumes another initialize isn't defined. Otherwise this - # method may need to be prepended. - def initialize(attributes = nil) - if attributes.is_a?(Hash) - attr = attributes.symbolize_keys - - if attr.key?(:state) && !attr.key?(:state_id) - value = attr.delete(:state) - state_id = self.class.available_states[value] - attributes[:state_id] = state_id if state_id - end - end - - super(attributes) - end - # We want to use optimistic lock for cases when only title or description are involved # http://api.rubyonrails.org/classes/ActiveRecord/Locking/Optimistic.html def locking_enabled? diff --git a/app/models/issue.rb b/app/models/issue.rb index 3f3e6b2f31a..7e5a94fc0a1 100644 --- a/app/models/issue.rb +++ b/app/models/issue.rb @@ -77,7 +77,7 @@ class Issue < ApplicationRecord attr_spammable :title, spam_title: true attr_spammable :description, spam_description: true - state_machine :state_id, initial: :opened do + state_machine :state_id, initial: :opened, initialize: false do event :close do transition [:opened] => :closed end diff --git a/app/models/merge_request.rb b/app/models/merge_request.rb index e92042d1056..93234cbdfe1 100644 --- a/app/models/merge_request.rb +++ b/app/models/merge_request.rb @@ -103,7 +103,7 @@ class MergeRequest < ApplicationRecord super + [:merged, :locked] end - state_machine :state_id, initial: :opened do + state_machine :state_id, initial: :opened, initialize: false do event :close do transition [:opened] => :closed end diff --git a/changelogs/unreleased/7597-add-template-repository-usage-to-the-usage-ping.yml b/changelogs/unreleased/7597-add-template-repository-usage-to-the-usage-ping.yml new file mode 100644 index 00000000000..f9479c3eef4 --- /dev/null +++ b/changelogs/unreleased/7597-add-template-repository-usage-to-the-usage-ping.yml @@ -0,0 +1,5 @@ +--- +title: Add template repository usage to the usage ping +merge_request: 20126 +author: minghuan lei +type: changed diff --git a/config/gitlab.yml.example b/config/gitlab.yml.example index a5486e450d4..711fd4ef3c2 100644 --- a/config/gitlab.yml.example +++ b/config/gitlab.yml.example @@ -321,8 +321,8 @@ production: &base # external_https: ["1.1.1.1:443", "[2001::1]:443"] # If defined, enables custom domain and certificate support in GitLab Pages # File that contains the shared secret key for verifying access for gitlab-pages. - # Default is '.gitlab_pages_shared_secret' relative to Rails.root (i.e. root of the GitLab app). - # secret_file: /home/git/gitlab/.gitlab_pages_shared_secret + # Default is '.gitlab_pages_secret' relative to Rails.root (i.e. root of the GitLab app). + # secret_file: /home/git/gitlab/.gitlab_pages_secret ## Mattermost ## For enabling Add to Mattermost button diff --git a/config/initializers/1_settings.rb b/config/initializers/1_settings.rb index df4f49524bc..f3635613339 100644 --- a/config/initializers/1_settings.rb +++ b/config/initializers/1_settings.rb @@ -291,7 +291,7 @@ Settings.pages['url'] ||= Settings.__send__(:build_pages_url) Settings.pages['external_http'] ||= false unless Settings.pages['external_http'].present? Settings.pages['external_https'] ||= false unless Settings.pages['external_https'].present? Settings.pages['artifacts_server'] ||= Settings.pages['enabled'] if Settings.pages['artifacts_server'].nil? -Settings.pages['secret_file'] ||= Rails.root.join('.gitlab_pages_shared_secret') +Settings.pages['secret_file'] ||= Rails.root.join('.gitlab_pages_secret') # # Geo diff --git a/doc/development/go_guide/index.md b/doc/development/go_guide/index.md index 33dd9dd9b6f..724bc240bc2 100644 --- a/doc/development/go_guide/index.md +++ b/doc/development/go_guide/index.md @@ -336,6 +336,49 @@ Generated docker images should have the program at their `Entrypoint` to create portable commands. That way, anyone can run the image, and without parameters it will display its help message (if `cli` has been used). +## Distributing Go binaries + +With the exception of [GitLab Runner](https://gitlab.com/gitlab-org/gitlab-runner), +which publishes its own binaries, our Go binaries are created by projects +managed by the [Distribution group](https://about.gitlab.com/handbook/product/categories/#distribution-group). + +The [Omnibus GitLab](https://gitlab.com/gitlab-org/omnibus-gitlab) project creates a +single, monolithic operating system package containing all the binaries, while +the [Cloud-Native GitLab (CNG)](https://gitlab.com/gitlab-org/build/CNG) project +publishes a set of Docker images and Helm charts to glue them together. + +Both approaches use the same version of Go for all projects, so it's important +to ensure all our Go-using projects have at least one Go version in common in +their test matrices. You can check the version of Go currently being used by +[Omnibus](https://gitlab.com/gitlab-org/gitlab-omnibus-builder/blob/master/docker/Dockerfile_debian_10#L59), +and the version being used for [CNG](https://gitlab.com/gitlab-org/build/cng/blob/master/ci_files/variables.yml#L12). + +### Updating Go version + +We should always use a [supported version](https://golang.org/doc/devel/release.html#policy) +of Go, i.e., one of the three most recent minor releases, and should always use +the most recent patch-level for that version, as it may contain security fixes. + +Changing the version affects every project being compiled, so it's important to +ensure that all projects have been updated to test against the new Go version +before changing the package builders to use it. Despite [Go's compatibility promise](https://golang.org/doc/go1compat), +changes between minor versions can expose bugs or cause problems in our projects. + +Once you've picked a new Go version to use, the steps to update Omnibus and CNG +are: + +- [Create a merge request in the CNG project](https://gitlab.com/gitlab-org/build/CNG/edit/master/ci_files/variables.yml?branch_name=update-go-version), + updating the `GO_VERSION` in `ci_files/variables.yml`. +- Create a merge request in the [`gitlab-omnibus-builder` project](https://gitlab.com/gitlab-org/gitlab-omnibus-builder), + updating every file in the `docker/` directory so the `GO_VERSION` is set + appropriately. [Here's an example](https://gitlab.com/gitlab-org/gitlab-omnibus-builder/merge_requests/125/diffs). +- Tag a new release of `gitlab-omnibus-builder` containing the change. +- [Create a merge request in the `gitlab-omnibus` project](https://gitlab.com/gitlab-org/omnibus-gitlab/edit/master/.gitlab-ci.yml?branch_name=update-gitlab-omnibus-builder-version), + updating the `BUILDER_IMAGE_REVISION` to match the newly-created tag. + +To reduce unnecessary differences between two distribution methods, Omnibus and +CNG **should always use the same Go version**. + --- [Return to Development documentation](../README.md). diff --git a/lib/banzai/filter/autolink_filter.rb b/lib/banzai/filter/autolink_filter.rb index 5f2cbc24c60..4723bfbf261 100644 --- a/lib/banzai/filter/autolink_filter.rb +++ b/lib/banzai/filter/autolink_filter.rb @@ -121,7 +121,7 @@ module Banzai def autolink_filter(text) Gitlab::StringRegexMarker.new(CGI.unescapeHTML(text), text.html_safe).mark(LINK_PATTERN) do |link, left:, right:| - autolink_match(link) + autolink_match(link).html_safe end end diff --git a/lib/banzai/filter/spaced_link_filter.rb b/lib/banzai/filter/spaced_link_filter.rb index ee7f10ebdf6..101b55a49e4 100644 --- a/lib/banzai/filter/spaced_link_filter.rb +++ b/lib/banzai/filter/spaced_link_filter.rb @@ -77,7 +77,7 @@ module Banzai def spaced_link_filter(text) Gitlab::StringRegexMarker.new(CGI.unescapeHTML(text), text.html_safe).mark(LINK_OR_IMAGE_PATTERN) do |link, left:, right:| - spaced_link_match(link) + spaced_link_match(link).html_safe end end diff --git a/lib/gitlab/dependency_linker/base_linker.rb b/lib/gitlab/dependency_linker/base_linker.rb index ffad00fa7d7..dd7ab92c6ae 100644 --- a/lib/gitlab/dependency_linker/base_linker.rb +++ b/lib/gitlab/dependency_linker/base_linker.rb @@ -62,7 +62,7 @@ module Gitlab end def link_tag(name, url) - %{#{ERB::Util.html_escape_once(name)}} + %{#{ERB::Util.html_escape_once(name)}}.html_safe end # Links package names based on regex. diff --git a/lib/gitlab/diff/inline_diff_marker.rb b/lib/gitlab/diff/inline_diff_marker.rb index 1bbde1ffd2a..29dff699ba5 100644 --- a/lib/gitlab/diff/inline_diff_marker.rb +++ b/lib/gitlab/diff/inline_diff_marker.rb @@ -9,7 +9,7 @@ module Gitlab def mark(line_inline_diffs, mode: nil) super(line_inline_diffs) do |text, left:, right:| - %{#{text}} + %{#{text}}.html_safe end end diff --git a/spec/factories/ci/builds.rb b/spec/factories/ci/builds.rb index 0bd39d4cdcf..ecb1f1996d9 100644 --- a/spec/factories/ci/builds.rb +++ b/spec/factories/ci/builds.rb @@ -373,6 +373,14 @@ FactoryBot.define do end end + trait :license_management do + options do + { + artifacts: { reports: { license_management: 'gl-license-management-report.json' } } + } + end + end + trait :non_playable do status { 'created' } self.when { 'manual' } diff --git a/spec/javascripts/pipelines/graph/job_item_spec.js b/spec/frontend/pipelines/graph/job_item_spec.js similarity index 51% rename from spec/javascripts/pipelines/graph/job_item_spec.js rename to spec/frontend/pipelines/graph/job_item_spec.js index 1cdb0aff524..943ef9d3531 100644 --- a/spec/javascripts/pipelines/graph/job_item_spec.js +++ b/spec/frontend/pipelines/graph/job_item_spec.js @@ -1,10 +1,13 @@ -import Vue from 'vue'; +import { trimText } from 'helpers/text_helper'; +import { mount } from '@vue/test-utils'; import JobItem from '~/pipelines/components/graph/job_item.vue'; -import mountComponent from 'spec/helpers/vue_mount_component_helper'; describe('pipeline graph job item', () => { - const JobComponent = Vue.extend(JobItem); - let component; + let wrapper; + + const createWrapper = propsData => { + wrapper = mount(JobItem, { sync: false, attachToDocument: true, propsData }); + }; const delayedJobFixture = getJSONFixture('jobs/delayed.json'); const mockJob = { @@ -28,27 +31,25 @@ describe('pipeline graph job item', () => { }; afterEach(() => { - component.$destroy(); + wrapper.destroy(); }); describe('name with link', () => { it('should render the job name and status with a link', done => { - component = mountComponent(JobComponent, { job: mockJob }); + createWrapper({ job: mockJob }); - Vue.nextTick(() => { - const link = component.$el.querySelector('a'); + wrapper.vm.$nextTick(() => { + const link = wrapper.find('a'); - expect(link.getAttribute('href')).toEqual(mockJob.status.details_path); + expect(link.attributes('href')).toBe(mockJob.status.details_path); - expect(link.getAttribute('data-original-title')).toEqual( + expect(link.attributes('data-original-title')).toEqual( `${mockJob.name} - ${mockJob.status.label}`, ); - expect(component.$el.querySelector('.js-status-icon-success')).toBeDefined(); + expect(wrapper.find('.js-status-icon-success')).toBeDefined(); - expect(component.$el.querySelector('.ci-status-text').textContent.trim()).toEqual( - mockJob.name, - ); + expect(trimText(wrapper.find('.ci-status-text').text())).toBe(mockJob.name); done(); }); @@ -57,7 +58,7 @@ describe('pipeline graph job item', () => { describe('name without link', () => { it('it should render status and name', () => { - component = mountComponent(JobComponent, { + createWrapper({ job: { id: 4257, name: 'test', @@ -72,36 +73,34 @@ describe('pipeline graph job item', () => { }, }); - expect(component.$el.querySelector('.js-status-icon-success')).toBeDefined(); - expect(component.$el.querySelector('a')).toBeNull(); + expect(wrapper.find('.js-status-icon-success')).toBeDefined(); + expect(wrapper.find('a').exists()).toBe(false); - expect(component.$el.querySelector('.ci-status-text').textContent.trim()).toEqual( - mockJob.name, - ); + expect(trimText(wrapper.find('.ci-status-text').text())).toEqual(mockJob.name); }); }); describe('action icon', () => { it('it should render the action icon', () => { - component = mountComponent(JobComponent, { job: mockJob }); + createWrapper({ job: mockJob }); - expect(component.$el.querySelector('a.ci-action-icon-container')).toBeDefined(); - expect(component.$el.querySelector('i.ci-action-icon-wrapper')).toBeDefined(); + expect(wrapper.find('a.ci-action-icon-container')).toBeDefined(); + expect(wrapper.find('i.ci-action-icon-wrapper')).toBeDefined(); }); }); it('should render provided class name', () => { - component = mountComponent(JobComponent, { + createWrapper({ job: mockJob, cssClassJobName: 'css-class-job-name', }); - expect(component.$el.querySelector('a').classList.contains('css-class-job-name')).toBe(true); + expect(wrapper.find('a').classes()).toContain('css-class-job-name'); }); describe('status label', () => { it('should not render status label when it is not provided', () => { - component = mountComponent(JobComponent, { + createWrapper({ job: { id: 4258, name: 'test', @@ -111,15 +110,13 @@ describe('pipeline graph job item', () => { }, }); - expect( - component.$el - .querySelector('.js-job-component-tooltip') - .getAttribute('data-original-title'), - ).toEqual('test'); + expect(wrapper.find('.js-job-component-tooltip').attributes('data-original-title')).toBe( + 'test', + ); }); it('should not render status label when it is provided', () => { - component = mountComponent(JobComponent, { + createWrapper({ job: { id: 4259, name: 'test', @@ -131,25 +128,21 @@ describe('pipeline graph job item', () => { }, }); - expect( - component.$el - .querySelector('.js-job-component-tooltip') - .getAttribute('data-original-title'), - ).toEqual('test - success'); + expect(wrapper.find('.js-job-component-tooltip').attributes('data-original-title')).toEqual( + 'test - success', + ); }); }); describe('for delayed job', () => { it('displays remaining time in tooltip', () => { - component = mountComponent(JobComponent, { + createWrapper({ job: delayedJobFixture, }); - expect( - component.$el - .querySelector('.js-pipeline-graph-job-link') - .getAttribute('data-original-title'), - ).toEqual(`delayed job - delayed manual action (${component.remainingTime})`); + expect(wrapper.find('.js-pipeline-graph-job-link').attributes('data-original-title')).toEqual( + `delayed job - delayed manual action (${wrapper.vm.remainingTime})`, + ); }); }); }); diff --git a/spec/frontend/pipelines/graph/linked_pipeline_spec.js b/spec/frontend/pipelines/graph/linked_pipeline_spec.js new file mode 100644 index 00000000000..c355d653203 --- /dev/null +++ b/spec/frontend/pipelines/graph/linked_pipeline_spec.js @@ -0,0 +1,127 @@ +import { mount } from '@vue/test-utils'; +import LinkedPipelineComponent from '~/pipelines/components/graph/linked_pipeline.vue'; + +import mockData from './linked_pipelines_mock_data'; + +const mockPipeline = mockData.triggered[0]; + +describe('Linked pipeline', () => { + let wrapper; + + afterEach(() => { + wrapper.destroy(); + }); + + describe('rendered output', () => { + const props = { + pipeline: mockPipeline, + }; + + beforeEach(() => { + wrapper = mount(LinkedPipelineComponent, { + sync: false, + attachToDocument: true, + propsData: props, + }); + }); + + it('should render a list item as the containing element', () => { + expect(wrapper.is('li')).toBe(true); + }); + + it('should render a button', () => { + const linkElement = wrapper.find('.js-linked-pipeline-content'); + + expect(linkElement.exists()).toBe(true); + }); + + it('should render the project name', () => { + expect(wrapper.text()).toContain(props.pipeline.project.name); + }); + + it('should render an svg within the status container', () => { + const pipelineStatusElement = wrapper.find('.js-linked-pipeline-status'); + + expect(pipelineStatusElement.find('svg').exists()).toBe(true); + }); + + it('should render the pipeline status icon svg', () => { + expect(wrapper.find('.js-ci-status-icon-running').exists()).toBe(true); + expect(wrapper.find('.js-ci-status-icon-running').html()).toContain(' { + expect(wrapper.find('.js-linked-pipeline-status').exists()).toBe(true); + }); + + it('should render the pipeline id', () => { + expect(wrapper.text()).toContain(`#${props.pipeline.id}`); + }); + + it('should correctly compute the tooltip text', () => { + expect(wrapper.vm.tooltipText).toContain(mockPipeline.project.name); + expect(wrapper.vm.tooltipText).toContain(mockPipeline.details.status.label); + }); + + it('should render the tooltip text as the title attribute', () => { + const tooltipRef = wrapper.find('.js-linked-pipeline-content'); + const titleAttr = tooltipRef.attributes('data-original-title'); + + expect(titleAttr).toContain(mockPipeline.project.name); + expect(titleAttr).toContain(mockPipeline.details.status.label); + }); + + it('does not render the loading icon when isLoading is false', () => { + expect(wrapper.find('.js-linked-pipeline-loading').exists()).toBe(false); + }); + }); + + describe('when isLoading is true', () => { + const props = { + pipeline: { ...mockPipeline, isLoading: true }, + }; + + beforeEach(() => { + wrapper = mount(LinkedPipelineComponent, { + sync: false, + attachToDocument: true, + propsData: props, + }); + }); + + it('renders a loading icon', () => { + expect(wrapper.find('.js-linked-pipeline-loading').exists()).toBe(true); + }); + }); + + describe('on click', () => { + const props = { + pipeline: mockPipeline, + }; + + beforeEach(() => { + wrapper = mount(LinkedPipelineComponent, { + sync: false, + attachToDocument: true, + propsData: props, + }); + }); + + it('emits `pipelineClicked` event', () => { + jest.spyOn(wrapper.vm, '$emit'); + wrapper.find('button').trigger('click'); + + expect(wrapper.vm.$emit).toHaveBeenCalledWith('pipelineClicked'); + }); + + it('should emit `bv::hide::tooltip` to close the tooltip', () => { + jest.spyOn(wrapper.vm.$root, '$emit'); + wrapper.find('button').trigger('click'); + + expect(wrapper.vm.$root.$emit.mock.calls[0]).toEqual([ + 'bv::hide::tooltip', + 'js-linked-pipeline-132', + ]); + }); + }); +}); diff --git a/spec/frontend/pipelines/graph/linked_pipelines_mock_data.js b/spec/frontend/pipelines/graph/linked_pipelines_mock_data.js new file mode 100644 index 00000000000..f794b8484a7 --- /dev/null +++ b/spec/frontend/pipelines/graph/linked_pipelines_mock_data.js @@ -0,0 +1,407 @@ +export default { + triggered_by: { + id: 129, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/129', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/129', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: '7-5-stable', + path: '/gitlab-org/gitlab-foss/commits/7-5-stable', + tag: false, + branch: true, + }, + commit: { + id: '23433d4d8b20d7e45c103d0b6048faad38a130ab', + short_id: '23433d4d', + title: 'Version 7.5.0.rc1', + created_at: '2014-11-17T15:44:14.000+01:00', + parent_ids: ['30ac909f30f58d319b42ed1537664483894b18cd'], + message: 'Version 7.5.0.rc1\n', + author_name: 'Jacob Vosmaer', + author_email: 'contact@jacobvosmaer.nl', + authored_date: '2014-11-17T15:44:14.000+01:00', + committer_name: 'Jacob Vosmaer', + committer_email: 'contact@jacobvosmaer.nl', + committed_date: '2014-11-17T15:44:14.000+01:00', + author_gravatar_url: + 'http://www.gravatar.com/avatar/e66d11c0eedf8c07b3b18fca46599807?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/23433d4d8b20d7e45c103d0b6048faad38a130ab', + commit_path: '/gitlab-org/gitlab-foss/commit/23433d4d8b20d7e45c103d0b6048faad38a130ab', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/129/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/129/cancel', + created_at: '2017-05-24T14:46:20.090Z', + updated_at: '2017-05-24T14:46:29.906Z', + }, + triggered: [ + { + id: 132, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/132', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/132', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: 'b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + short_id: 'b9d58c4c', + title: 'getting user keys publically through http without any authentication, the github…', + created_at: '2013-10-03T12:50:33.000+05:30', + parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], + message: + 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n\nchangelog updated to include ssh key retrieval feature update\n', + author_name: 'devaroop', + author_email: 'devaroop123@yahoo.co.in', + authored_date: '2013-10-02T20:39:29.000+05:30', + committer_name: 'devaroop', + committer_email: 'devaroop123@yahoo.co.in', + committed_date: '2013-10-03T12:50:33.000+05:30', + author_gravatar_url: + 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + commit_path: '/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/132/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/132/cancel', + created_at: '2017-05-24T14:46:24.644Z', + updated_at: '2017-05-24T14:48:55.226Z', + }, + { + id: 133, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/133', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/133', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: 'b6bd4856a33df3d144be66c4ed1f1396009bb08b', + short_id: 'b6bd4856', + title: 'getting user keys publically through http without any authentication, the github…', + created_at: '2013-10-02T20:39:29.000+05:30', + parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], + message: + 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n', + author_name: 'devaroop', + author_email: 'devaroop123@yahoo.co.in', + authored_date: '2013-10-02T20:39:29.000+05:30', + committer_name: 'devaroop', + committer_email: 'devaroop123@yahoo.co.in', + committed_date: '2013-10-02T20:39:29.000+05:30', + author_gravatar_url: + 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', + commit_path: '/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/133/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/133/cancel', + created_at: '2017-05-24T14:46:24.648Z', + updated_at: '2017-05-24T14:48:59.673Z', + }, + { + id: 130, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/130', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/130', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: '6d7ced4a2311eeff037c5575cca1868a6d3f586f', + short_id: '6d7ced4a', + title: 'Whitespace fixes to patch', + created_at: '2013-10-08T13:53:22.000-05:00', + parent_ids: ['1875141a963a4238bda29011d8f7105839485253'], + message: 'Whitespace fixes to patch\n', + author_name: 'Dale Hamel', + author_email: 'dale.hamel@srvthe.net', + authored_date: '2013-10-08T13:53:22.000-05:00', + committer_name: 'Dale Hamel', + committer_email: 'dale.hamel@invenia.ca', + committed_date: '2013-10-08T13:53:22.000-05:00', + author_gravatar_url: + 'http://www.gravatar.com/avatar/cd08930e69fa5ad1a669206e7bafe476?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', + commit_path: '/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/130/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/130/cancel', + created_at: '2017-05-24T14:46:24.630Z', + updated_at: '2017-05-24T14:49:45.091Z', + }, + { + id: 131, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/132', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/132', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: 'b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + short_id: 'b9d58c4c', + title: 'getting user keys publically through http without any authentication, the github…', + created_at: '2013-10-03T12:50:33.000+05:30', + parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], + message: + 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n\nchangelog updated to include ssh key retrieval feature update\n', + author_name: 'devaroop', + author_email: 'devaroop123@yahoo.co.in', + authored_date: '2013-10-02T20:39:29.000+05:30', + committer_name: 'devaroop', + committer_email: 'devaroop123@yahoo.co.in', + committed_date: '2013-10-03T12:50:33.000+05:30', + author_gravatar_url: + 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + commit_path: '/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/132/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/132/cancel', + created_at: '2017-05-24T14:46:24.644Z', + updated_at: '2017-05-24T14:48:55.226Z', + }, + { + id: 134, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/133', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/133', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: 'b6bd4856a33df3d144be66c4ed1f1396009bb08b', + short_id: 'b6bd4856', + title: 'getting user keys publically through http without any authentication, the github…', + created_at: '2013-10-02T20:39:29.000+05:30', + parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], + message: + 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n', + author_name: 'devaroop', + author_email: 'devaroop123@yahoo.co.in', + authored_date: '2013-10-02T20:39:29.000+05:30', + committer_name: 'devaroop', + committer_email: 'devaroop123@yahoo.co.in', + committed_date: '2013-10-02T20:39:29.000+05:30', + author_gravatar_url: + 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', + commit_path: '/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/133/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/133/cancel', + created_at: '2017-05-24T14:46:24.648Z', + updated_at: '2017-05-24T14:48:59.673Z', + }, + { + id: 135, + active: true, + path: '/gitlab-org/gitlab-foss/pipelines/130', + project: { + name: 'GitLabCE', + }, + details: { + status: { + icon: 'status_running', + text: 'running', + label: 'running', + group: 'running', + has_details: true, + details_path: '/gitlab-org/gitlab-foss/pipelines/130', + favicon: + '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', + }, + }, + flags: { + latest: false, + triggered: false, + stuck: false, + yaml_errors: false, + retryable: true, + cancelable: true, + }, + ref: { + name: 'crowd', + path: '/gitlab-org/gitlab-foss/commits/crowd', + tag: false, + branch: true, + }, + commit: { + id: '6d7ced4a2311eeff037c5575cca1868a6d3f586f', + short_id: '6d7ced4a', + title: 'Whitespace fixes to patch', + created_at: '2013-10-08T13:53:22.000-05:00', + parent_ids: ['1875141a963a4238bda29011d8f7105839485253'], + message: 'Whitespace fixes to patch\n', + author_name: 'Dale Hamel', + author_email: 'dale.hamel@srvthe.net', + authored_date: '2013-10-08T13:53:22.000-05:00', + committer_name: 'Dale Hamel', + committer_email: 'dale.hamel@invenia.ca', + committed_date: '2013-10-08T13:53:22.000-05:00', + author_gravatar_url: + 'http://www.gravatar.com/avatar/cd08930e69fa5ad1a669206e7bafe476?s=80&d=identicon', + commit_url: + 'http://localhost:3000/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', + commit_path: '/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', + }, + retry_path: '/gitlab-org/gitlab-foss/pipelines/130/retry', + cancel_path: '/gitlab-org/gitlab-foss/pipelines/130/cancel', + created_at: '2017-05-24T14:46:24.630Z', + updated_at: '2017-05-24T14:49:45.091Z', + }, + ], +}; diff --git a/spec/frontend/pipelines/pipeline_url_spec.js b/spec/frontend/pipelines/pipeline_url_spec.js new file mode 100644 index 00000000000..3c0c35e1f0f --- /dev/null +++ b/spec/frontend/pipelines/pipeline_url_spec.js @@ -0,0 +1,112 @@ +import $ from 'jquery'; +import { trimText } from 'helpers/text_helper'; +import { shallowMount } from '@vue/test-utils'; +import PipelineUrlComponent from '~/pipelines/components/pipeline_url.vue'; + +$.fn.popover = () => {}; + +describe('Pipeline Url Component', () => { + let wrapper; + + const createComponent = props => { + wrapper = shallowMount(PipelineUrlComponent, { + sync: false, + attachToDocument: true, + propsData: props, + }); + }; + + afterEach(() => { + wrapper.destroy(); + }); + + it('should render a table cell', () => { + createComponent({ + pipeline: { + id: 1, + path: 'foo', + flags: {}, + }, + autoDevopsHelpPath: 'foo', + }); + + expect(wrapper.attributes('class')).toContain('table-section'); + }); + + it('should render a link the provided path and id', () => { + createComponent({ + pipeline: { + id: 1, + path: 'foo', + flags: {}, + }, + autoDevopsHelpPath: 'foo', + }); + + expect(wrapper.find('.js-pipeline-url-link').attributes('href')).toBe('foo'); + + expect(wrapper.find('.js-pipeline-url-link span').text()).toBe('#1'); + }); + + it('should render latest, yaml invalid, merge request, and stuck flags when provided', () => { + createComponent({ + pipeline: { + id: 1, + path: 'foo', + flags: { + latest: true, + yaml_errors: true, + stuck: true, + merge_request_pipeline: true, + detached_merge_request_pipeline: true, + }, + }, + autoDevopsHelpPath: 'foo', + }); + + expect(wrapper.find('.js-pipeline-url-latest').text()).toContain('latest'); + + expect(wrapper.find('.js-pipeline-url-yaml').text()).toContain('yaml invalid'); + + expect(wrapper.find('.js-pipeline-url-stuck').text()).toContain('stuck'); + + expect(wrapper.find('.js-pipeline-url-detached').text()).toContain('detached'); + }); + + it('should render a badge for autodevops', () => { + createComponent({ + pipeline: { + id: 1, + path: 'foo', + flags: { + latest: true, + yaml_errors: true, + stuck: true, + auto_devops: true, + }, + }, + autoDevopsHelpPath: 'foo', + }); + + expect(trimText(wrapper.find('.js-pipeline-url-autodevops').text())).toEqual('Auto DevOps'); + }); + + it('should render error badge when pipeline has a failure reason set', () => { + createComponent({ + pipeline: { + id: 1, + path: 'foo', + flags: { + failure_reason: true, + }, + failure_reason: 'some reason', + }, + autoDevopsHelpPath: 'foo', + }); + + expect(wrapper.find('.js-pipeline-url-failure').text()).toContain('error'); + expect(wrapper.find('.js-pipeline-url-failure').attributes('data-original-title')).toContain( + 'some reason', + ); + }); +}); diff --git a/spec/javascripts/pipelines/graph/linked_pipeline_spec.js b/spec/javascripts/pipelines/graph/linked_pipeline_spec.js deleted file mode 100644 index 8d3abf094b6..00000000000 --- a/spec/javascripts/pipelines/graph/linked_pipeline_spec.js +++ /dev/null @@ -1,116 +0,0 @@ -import Vue from 'vue'; -import LinkedPipelineComponent from '~/pipelines/components/graph/linked_pipeline.vue'; -import mountComponent from 'spec/helpers/vue_mount_component_helper'; -import mockData from './linked_pipelines_mock_data'; - -const mockPipeline = mockData.triggered[0]; - -describe('Linked pipeline', () => { - const Component = Vue.extend(LinkedPipelineComponent); - let vm; - - afterEach(() => { - vm.$destroy(); - }); - - describe('rendered output', () => { - const props = { - pipeline: mockPipeline, - }; - - beforeEach(() => { - vm = mountComponent(Component, props); - }); - - it('should render a list item as the containing element', () => { - expect(vm.$el.tagName).toBe('LI'); - }); - - it('should render a button', () => { - const linkElement = vm.$el.querySelector('.js-linked-pipeline-content'); - - expect(linkElement).not.toBeNull(); - }); - - it('should render the project name', () => { - expect(vm.$el.innerText).toContain(props.pipeline.project.name); - }); - - it('should render an svg within the status container', () => { - const pipelineStatusElement = vm.$el.querySelector('.js-linked-pipeline-status'); - - expect(pipelineStatusElement.querySelector('svg')).not.toBeNull(); - }); - - it('should render the pipeline status icon svg', () => { - expect(vm.$el.querySelector('.js-ci-status-icon-running')).not.toBeNull(); - expect(vm.$el.querySelector('.js-ci-status-icon-running').innerHTML).toContain(' { - expect(vm.$el.querySelector('.js-linked-pipeline-status')).not.toBeNull(); - }); - - it('should render the pipeline id', () => { - expect(vm.$el.innerText).toContain(`#${props.pipeline.id}`); - }); - - it('should correctly compute the tooltip text', () => { - expect(vm.tooltipText).toContain(mockPipeline.project.name); - expect(vm.tooltipText).toContain(mockPipeline.details.status.label); - }); - - it('should render the tooltip text as the title attribute', () => { - const tooltipRef = vm.$el.querySelector('.js-linked-pipeline-content'); - const titleAttr = tooltipRef.getAttribute('data-original-title'); - - expect(titleAttr).toContain(mockPipeline.project.name); - expect(titleAttr).toContain(mockPipeline.details.status.label); - }); - - it('does not render the loading icon when isLoading is false', () => { - expect(vm.$el.querySelector('.js-linked-pipeline-loading')).toBeNull(); - }); - }); - - describe('when isLoading is true', () => { - const props = { - pipeline: { ...mockPipeline, isLoading: true }, - }; - - beforeEach(() => { - vm = mountComponent(Component, props); - }); - - it('renders a loading icon', () => { - expect(vm.$el.querySelector('.js-linked-pipeline-loading')).not.toBeNull(); - }); - }); - - describe('on click', () => { - const props = { - pipeline: mockPipeline, - }; - - beforeEach(() => { - vm = mountComponent(Component, props); - }); - - it('emits `pipelineClicked` event', () => { - spyOn(vm, '$emit'); - vm.$el.querySelector('button').click(); - - expect(vm.$emit).toHaveBeenCalledWith('pipelineClicked'); - }); - - it('should emit `bv::hide::tooltip` to close the tooltip', () => { - spyOn(vm.$root, '$emit'); - vm.$el.querySelector('button').click(); - - expect(vm.$root.$emit.calls.argsFor(0)).toEqual([ - 'bv::hide::tooltip', - 'js-linked-pipeline-132', - ]); - }); - }); -}); diff --git a/spec/javascripts/pipelines/graph/linked_pipelines_mock_data.js b/spec/javascripts/pipelines/graph/linked_pipelines_mock_data.js index f794b8484a7..3079d5e4e68 100644 --- a/spec/javascripts/pipelines/graph/linked_pipelines_mock_data.js +++ b/spec/javascripts/pipelines/graph/linked_pipelines_mock_data.js @@ -1,407 +1,3 @@ -export default { - triggered_by: { - id: 129, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/129', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/129', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: '7-5-stable', - path: '/gitlab-org/gitlab-foss/commits/7-5-stable', - tag: false, - branch: true, - }, - commit: { - id: '23433d4d8b20d7e45c103d0b6048faad38a130ab', - short_id: '23433d4d', - title: 'Version 7.5.0.rc1', - created_at: '2014-11-17T15:44:14.000+01:00', - parent_ids: ['30ac909f30f58d319b42ed1537664483894b18cd'], - message: 'Version 7.5.0.rc1\n', - author_name: 'Jacob Vosmaer', - author_email: 'contact@jacobvosmaer.nl', - authored_date: '2014-11-17T15:44:14.000+01:00', - committer_name: 'Jacob Vosmaer', - committer_email: 'contact@jacobvosmaer.nl', - committed_date: '2014-11-17T15:44:14.000+01:00', - author_gravatar_url: - 'http://www.gravatar.com/avatar/e66d11c0eedf8c07b3b18fca46599807?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/23433d4d8b20d7e45c103d0b6048faad38a130ab', - commit_path: '/gitlab-org/gitlab-foss/commit/23433d4d8b20d7e45c103d0b6048faad38a130ab', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/129/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/129/cancel', - created_at: '2017-05-24T14:46:20.090Z', - updated_at: '2017-05-24T14:46:29.906Z', - }, - triggered: [ - { - id: 132, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/132', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/132', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: 'b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - short_id: 'b9d58c4c', - title: 'getting user keys publically through http without any authentication, the github…', - created_at: '2013-10-03T12:50:33.000+05:30', - parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], - message: - 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n\nchangelog updated to include ssh key retrieval feature update\n', - author_name: 'devaroop', - author_email: 'devaroop123@yahoo.co.in', - authored_date: '2013-10-02T20:39:29.000+05:30', - committer_name: 'devaroop', - committer_email: 'devaroop123@yahoo.co.in', - committed_date: '2013-10-03T12:50:33.000+05:30', - author_gravatar_url: - 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - commit_path: '/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/132/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/132/cancel', - created_at: '2017-05-24T14:46:24.644Z', - updated_at: '2017-05-24T14:48:55.226Z', - }, - { - id: 133, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/133', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/133', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: 'b6bd4856a33df3d144be66c4ed1f1396009bb08b', - short_id: 'b6bd4856', - title: 'getting user keys publically through http without any authentication, the github…', - created_at: '2013-10-02T20:39:29.000+05:30', - parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], - message: - 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n', - author_name: 'devaroop', - author_email: 'devaroop123@yahoo.co.in', - authored_date: '2013-10-02T20:39:29.000+05:30', - committer_name: 'devaroop', - committer_email: 'devaroop123@yahoo.co.in', - committed_date: '2013-10-02T20:39:29.000+05:30', - author_gravatar_url: - 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', - commit_path: '/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/133/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/133/cancel', - created_at: '2017-05-24T14:46:24.648Z', - updated_at: '2017-05-24T14:48:59.673Z', - }, - { - id: 130, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/130', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/130', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: '6d7ced4a2311eeff037c5575cca1868a6d3f586f', - short_id: '6d7ced4a', - title: 'Whitespace fixes to patch', - created_at: '2013-10-08T13:53:22.000-05:00', - parent_ids: ['1875141a963a4238bda29011d8f7105839485253'], - message: 'Whitespace fixes to patch\n', - author_name: 'Dale Hamel', - author_email: 'dale.hamel@srvthe.net', - authored_date: '2013-10-08T13:53:22.000-05:00', - committer_name: 'Dale Hamel', - committer_email: 'dale.hamel@invenia.ca', - committed_date: '2013-10-08T13:53:22.000-05:00', - author_gravatar_url: - 'http://www.gravatar.com/avatar/cd08930e69fa5ad1a669206e7bafe476?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', - commit_path: '/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/130/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/130/cancel', - created_at: '2017-05-24T14:46:24.630Z', - updated_at: '2017-05-24T14:49:45.091Z', - }, - { - id: 131, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/132', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/132', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: 'b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - short_id: 'b9d58c4c', - title: 'getting user keys publically through http without any authentication, the github…', - created_at: '2013-10-03T12:50:33.000+05:30', - parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], - message: - 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n\nchangelog updated to include ssh key retrieval feature update\n', - author_name: 'devaroop', - author_email: 'devaroop123@yahoo.co.in', - authored_date: '2013-10-02T20:39:29.000+05:30', - committer_name: 'devaroop', - committer_email: 'devaroop123@yahoo.co.in', - committed_date: '2013-10-03T12:50:33.000+05:30', - author_gravatar_url: - 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - commit_path: '/gitlab-org/gitlab-foss/commit/b9d58c4cecd06be74c3cc32ccfb522b31544ab2e', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/132/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/132/cancel', - created_at: '2017-05-24T14:46:24.644Z', - updated_at: '2017-05-24T14:48:55.226Z', - }, - { - id: 134, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/133', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/133', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: 'b6bd4856a33df3d144be66c4ed1f1396009bb08b', - short_id: 'b6bd4856', - title: 'getting user keys publically through http without any authentication, the github…', - created_at: '2013-10-02T20:39:29.000+05:30', - parent_ids: ['e219cf7246c6a0495e4507deaffeba11e79f13b8'], - message: - 'getting user keys publically through http without any authentication, the github way. E.g: http://github.com/devaroop.keys\n', - author_name: 'devaroop', - author_email: 'devaroop123@yahoo.co.in', - authored_date: '2013-10-02T20:39:29.000+05:30', - committer_name: 'devaroop', - committer_email: 'devaroop123@yahoo.co.in', - committed_date: '2013-10-02T20:39:29.000+05:30', - author_gravatar_url: - 'http://www.gravatar.com/avatar/35df4b155ec66a3127d53459941cf8a2?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', - commit_path: '/gitlab-org/gitlab-foss/commit/b6bd4856a33df3d144be66c4ed1f1396009bb08b', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/133/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/133/cancel', - created_at: '2017-05-24T14:46:24.648Z', - updated_at: '2017-05-24T14:48:59.673Z', - }, - { - id: 135, - active: true, - path: '/gitlab-org/gitlab-foss/pipelines/130', - project: { - name: 'GitLabCE', - }, - details: { - status: { - icon: 'status_running', - text: 'running', - label: 'running', - group: 'running', - has_details: true, - details_path: '/gitlab-org/gitlab-foss/pipelines/130', - favicon: - '/assets/ci_favicons/dev/favicon_status_running-c3ad2fc53ea6079c174e5b6c1351ff349e99ec3af5a5622fb77b0fe53ea279c1.ico', - }, - }, - flags: { - latest: false, - triggered: false, - stuck: false, - yaml_errors: false, - retryable: true, - cancelable: true, - }, - ref: { - name: 'crowd', - path: '/gitlab-org/gitlab-foss/commits/crowd', - tag: false, - branch: true, - }, - commit: { - id: '6d7ced4a2311eeff037c5575cca1868a6d3f586f', - short_id: '6d7ced4a', - title: 'Whitespace fixes to patch', - created_at: '2013-10-08T13:53:22.000-05:00', - parent_ids: ['1875141a963a4238bda29011d8f7105839485253'], - message: 'Whitespace fixes to patch\n', - author_name: 'Dale Hamel', - author_email: 'dale.hamel@srvthe.net', - authored_date: '2013-10-08T13:53:22.000-05:00', - committer_name: 'Dale Hamel', - committer_email: 'dale.hamel@invenia.ca', - committed_date: '2013-10-08T13:53:22.000-05:00', - author_gravatar_url: - 'http://www.gravatar.com/avatar/cd08930e69fa5ad1a669206e7bafe476?s=80&d=identicon', - commit_url: - 'http://localhost:3000/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', - commit_path: '/gitlab-org/gitlab-foss/commit/6d7ced4a2311eeff037c5575cca1868a6d3f586f', - }, - retry_path: '/gitlab-org/gitlab-foss/pipelines/130/retry', - cancel_path: '/gitlab-org/gitlab-foss/pipelines/130/cancel', - created_at: '2017-05-24T14:46:24.630Z', - updated_at: '2017-05-24T14:49:45.091Z', - }, - ], -}; +import mockData from '../../../frontend/pipelines/graph/linked_pipelines_mock_data'; + +export default mockData; diff --git a/spec/javascripts/pipelines/pipeline_url_spec.js b/spec/javascripts/pipelines/pipeline_url_spec.js deleted file mode 100644 index aa196af2f33..00000000000 --- a/spec/javascripts/pipelines/pipeline_url_spec.js +++ /dev/null @@ -1,118 +0,0 @@ -import Vue from 'vue'; -import pipelineUrlComp from '~/pipelines/components/pipeline_url.vue'; - -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: {}, - }, - autoDevopsHelpPath: 'foo', - }, - }).$mount(); - - expect(component.$el.getAttribute('class')).toContain('table-section'); - }); - - it('should render a link the provided path and id', () => { - const component = new PipelineUrlComponent({ - propsData: { - pipeline: { - id: 1, - path: 'foo', - flags: {}, - }, - autoDevopsHelpPath: 'foo', - }, - }).$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 latest, yaml invalid, merge request, and stuck flags when provided', () => { - const component = new PipelineUrlComponent({ - propsData: { - pipeline: { - id: 1, - path: 'foo', - flags: { - latest: true, - yaml_errors: true, - stuck: true, - merge_request_pipeline: true, - detached_merge_request_pipeline: true, - }, - }, - autoDevopsHelpPath: 'foo', - }, - }).$mount(); - - expect(component.$el.querySelector('.js-pipeline-url-latest').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'); - - expect(component.$el.querySelector('.js-pipeline-url-detached').textContent).toContain( - 'detached', - ); - }); - - it('should render a badge for autodevops', () => { - const component = new PipelineUrlComponent({ - propsData: { - pipeline: { - id: 1, - path: 'foo', - flags: { - latest: true, - yaml_errors: true, - stuck: true, - auto_devops: true, - }, - }, - autoDevopsHelpPath: 'foo', - }, - }).$mount(); - - expect(component.$el.querySelector('.js-pipeline-url-autodevops').textContent.trim()).toEqual( - 'Auto DevOps', - ); - }); - - it('should render error badge when pipeline has a failure reason set', () => { - const component = new PipelineUrlComponent({ - propsData: { - pipeline: { - id: 1, - path: 'foo', - flags: { - failure_reason: true, - }, - failure_reason: 'some reason', - }, - autoDevopsHelpPath: 'foo', - }, - }).$mount(); - - expect(component.$el.querySelector('.js-pipeline-url-failure').textContent).toContain('error'); - expect( - component.$el.querySelector('.js-pipeline-url-failure').getAttribute('data-original-title'), - ).toContain('some reason'); - }); -}); diff --git a/spec/lib/gitlab/pages_spec.rb b/spec/lib/gitlab/pages_spec.rb index affa2ebab2a..aecbc74385e 100644 --- a/spec/lib/gitlab/pages_spec.rb +++ b/spec/lib/gitlab/pages_spec.rb @@ -3,10 +3,10 @@ require 'spec_helper' describe Gitlab::Pages do - let(:pages_shared_secret) { SecureRandom.random_bytes(Gitlab::Pages::SECRET_LENGTH) } + let(:pages_secret) { SecureRandom.random_bytes(Gitlab::Pages::SECRET_LENGTH) } before do - allow(described_class).to receive(:secret).and_return(pages_shared_secret) + allow(described_class).to receive(:secret).and_return(pages_secret) end describe '.verify_api_request' do diff --git a/spec/lib/gitlab/string_range_marker_spec.rb b/spec/lib/gitlab/string_range_marker_spec.rb index 7ed43db3d10..ef9be7cd992 100644 --- a/spec/lib/gitlab/string_range_marker_spec.rb +++ b/spec/lib/gitlab/string_range_marker_spec.rb @@ -9,7 +9,7 @@ describe Gitlab::StringRangeMarker do inline_diffs = [2..5] described_class.new(raw, rich).mark(inline_diffs) do |text, left:, right:| - "LEFT#{text}RIGHT" + "LEFT#{text}RIGHT".html_safe end end diff --git a/spec/lib/gitlab/string_regex_marker_spec.rb b/spec/lib/gitlab/string_regex_marker_spec.rb index 2b19edbe7f9..2ab1ccc447b 100644 --- a/spec/lib/gitlab/string_regex_marker_spec.rb +++ b/spec/lib/gitlab/string_regex_marker_spec.rb @@ -10,7 +10,7 @@ describe Gitlab::StringRegexMarker do subject do described_class.new(raw, rich).mark(/"[^"]+":\s*"(?[^"]+)"/, group: :name) do |text, left:, right:| - %{#{text}} + %{#{text}}.html_safe end end @@ -26,7 +26,7 @@ describe Gitlab::StringRegexMarker do subject do described_class.new(raw, rich).mark(/<[a-z]>/) do |text, left:, right:| - %{#{text}} + %{#{text}}.html_safe end end diff --git a/spec/requests/api/internal/pages_spec.rb b/spec/requests/api/internal/pages_spec.rb index 03bf748b471..23bbd0681d6 100644 --- a/spec/requests/api/internal/pages_spec.rb +++ b/spec/requests/api/internal/pages_spec.rb @@ -4,10 +4,10 @@ require 'spec_helper' describe API::Internal::Pages do describe "GET /internal/pages" do - let(:pages_shared_secret) { SecureRandom.random_bytes(Gitlab::Pages::SECRET_LENGTH) } + let(:pages_secret) { SecureRandom.random_bytes(Gitlab::Pages::SECRET_LENGTH) } before do - allow(Gitlab::Pages).to receive(:secret).and_return(pages_shared_secret) + allow(Gitlab::Pages).to receive(:secret).and_return(pages_secret) end def query_host(host, headers = {})