Commit 4f418b41 authored by GitLab Bot's avatar GitLab Bot

Merge remote-tracking branch 'upstream/master' into ce-to-ee-2018-10-24

# Conflicts:
#	.gitlab-ci.yml
#	app/helpers/groups_helper.rb
#	app/views/layouts/_page.html.haml
#	doc/ci/yaml/README.md
#	doc/topics/autodevops/index.md
#	locale/gitlab.pot

[ci skip]
parents 5877353d 605e952e
...@@ -80,6 +80,7 @@ stages: ...@@ -80,6 +80,7 @@ stages:
- mysql:5.7 - mysql:5.7
- redis:alpine - redis:alpine
<<<<<<< HEAD
# BEGIN EE-only service helpers # BEGIN EE-only service helpers
.use-pg-9-6: &use-pg-9-6 .use-pg-9-6: &use-pg-9-6
...@@ -106,6 +107,8 @@ stages: ...@@ -106,6 +107,8 @@ stages:
# END EE-only service helpers # END EE-only service helpers
=======
>>>>>>> upstream/master
.rails5: &rails5 .rails5: &rails5
allow_failure: true allow_failure: true
only: only:
...@@ -1192,5 +1195,9 @@ schedule:review_apps_cleanup: ...@@ -1192,5 +1195,9 @@ schedule:review_apps_cleanup:
- schedules@gitlab-org/gitlab-ee - schedules@gitlab-org/gitlab-ee
kubernetes: active kubernetes: active
except: except:
<<<<<<< HEAD
=======
- master
>>>>>>> upstream/master
- tags - tags
- /(^docs[\/-].*|.*-docs$)/ - /(^docs[\/-].*|.*-docs$)/
...@@ -16,7 +16,6 @@ Set the title to: `[Security] Description of the original issue` ...@@ -16,7 +16,6 @@ Set the title to: `[Security] Description of the original issue`
- [ ] Add a link to the MR to the [links section](#links) - [ ] Add a link to the MR to the [links section](#links)
- [ ] Add a link to an EE MR if required - [ ] Add a link to an EE MR if required
- [ ] Make sure the MR remains in-progress and gets approved after the review cycle, **but never merged**. - [ ] Make sure the MR remains in-progress and gets approved after the review cycle, **but never merged**.
- [ ] Assign the MR to a RM once is reviewed and ready to be merged. Check the [RM list] to see who to ping.
#### Backports #### Backports
...@@ -26,7 +25,8 @@ Set the title to: `[Security] Description of the original issue` ...@@ -26,7 +25,8 @@ Set the title to: `[Security] Description of the original issue`
- [ ] Create the branch `security-X-Y` from `X-Y-stable` if it doesn't exist (and make sure it's up to date with stable) - [ ] Create the branch `security-X-Y` from `X-Y-stable` if it doesn't exist (and make sure it's up to date with stable)
- [ ] Create each MR targetting the security branch `security-X-Y` - [ ] Create each MR targetting the security branch `security-X-Y`
- [ ] Add the ~security label and prefix with the version `WIP: [X.Y]` the title of the MR - [ ] Add the ~security label and prefix with the version `WIP: [X.Y]` the title of the MR
- [ ] Make sure all MRs have a link in the [links section](#links) and are assigned to a Release Manager. - [ ] Add the ~"Merge into Security" label to all of the MRs.
- [ ] Make sure all MRs have a link in the [links section](#links)
[secpick documentation]: https://gitlab.com/gitlab-org/release/docs/blob/master/general/security/developer.md#secpick-script [secpick documentation]: https://gitlab.com/gitlab-org/release/docs/blob/master/general/security/developer.md#secpick-script
......
...@@ -432,8 +432,7 @@ end ...@@ -432,8 +432,7 @@ end
gem 'gitaly-proto', '~> 0.118.1', require: 'gitaly' gem 'gitaly-proto', '~> 0.118.1', require: 'gitaly'
gem 'grpc', '~> 1.15.0' gem 'grpc', '~> 1.15.0'
# Locked until https://github.com/google/protobuf/issues/4210 is closed gem 'google-protobuf', '~> 3.6'
gem 'google-protobuf', '= 3.5.1'
gem 'toml-rb', '~> 1.0.0', require: false gem 'toml-rb', '~> 1.0.0', require: false
......
...@@ -328,7 +328,7 @@ GEM ...@@ -328,7 +328,7 @@ GEM
mime-types (~> 3.0) mime-types (~> 3.0)
representable (~> 3.0) representable (~> 3.0)
retriable (>= 2.0, < 4.0) retriable (>= 2.0, < 4.0)
google-protobuf (3.5.1) google-protobuf (3.6.1)
googleapis-common-protos-types (1.0.2) googleapis-common-protos-types (1.0.2)
google-protobuf (~> 3.0) google-protobuf (~> 3.0)
googleauth (0.6.6) googleauth (0.6.6)
...@@ -1040,7 +1040,7 @@ DEPENDENCIES ...@@ -1040,7 +1040,7 @@ DEPENDENCIES
gitlab_omniauth-ldap (~> 2.0.4) gitlab_omniauth-ldap (~> 2.0.4)
gon (~> 6.2) gon (~> 6.2)
google-api-client (~> 0.23) google-api-client (~> 0.23)
google-protobuf (= 3.5.1) google-protobuf (~> 3.6)
gpgme gpgme
grape (~> 1.1) grape (~> 1.1)
grape-entity (~> 0.7.1) grape-entity (~> 0.7.1)
......
...@@ -331,7 +331,7 @@ GEM ...@@ -331,7 +331,7 @@ GEM
mime-types (~> 3.0) mime-types (~> 3.0)
representable (~> 3.0) representable (~> 3.0)
retriable (>= 2.0, < 4.0) retriable (>= 2.0, < 4.0)
google-protobuf (3.5.1) google-protobuf (3.6.1)
googleapis-common-protos-types (1.0.2) googleapis-common-protos-types (1.0.2)
google-protobuf (~> 3.0) google-protobuf (~> 3.0)
googleauth (0.6.6) googleauth (0.6.6)
...@@ -1049,7 +1049,7 @@ DEPENDENCIES ...@@ -1049,7 +1049,7 @@ DEPENDENCIES
gitlab_omniauth-ldap (~> 2.0.4) gitlab_omniauth-ldap (~> 2.0.4)
gon (~> 6.2) gon (~> 6.2)
google-api-client (~> 0.23) google-api-client (~> 0.23)
google-protobuf (= 3.5.1) google-protobuf (~> 3.6)
gpgme gpgme
grape (~> 1.1) grape (~> 1.1)
grape-entity (~> 0.7.1) grape-entity (~> 0.7.1)
......
...@@ -6,10 +6,12 @@ import Pager from './pager'; ...@@ -6,10 +6,12 @@ import Pager from './pager';
import { localTimeAgo } from './lib/utils/datetime_utility'; import { localTimeAgo } from './lib/utils/datetime_utility';
export default class Activities { export default class Activities {
constructor() { constructor(container = '') {
Pager.init(20, true, false, data => data, this.updateTooltips); this.container = container;
$('.event-filter-link').on('click', (e) => { Pager.init(20, true, false, data => data, this.updateTooltips, this.container);
$('.event-filter-link').on('click', e => {
e.preventDefault(); e.preventDefault();
this.toggleFilter(e.currentTarget); this.toggleFilter(e.currentTarget);
this.reloadActivities(); this.reloadActivities();
...@@ -22,7 +24,7 @@ export default class Activities { ...@@ -22,7 +24,7 @@ export default class Activities {
reloadActivities() { reloadActivities() {
$('.content_list').html(''); $('.content_list').html('');
Pager.init(20, true, false, data => data, this.updateTooltips); Pager.init(20, true, false, data => data, this.updateTooltips, this.container);
} }
toggleFilter(sender) { toggleFilter(sender) {
......
<script> <script>
import { mapActions, mapGetters, mapState } from 'vuex'; import { mapActions, mapGetters, mapState } from 'vuex';
import { TooltipDirective as Tooltip } from '@gitlab-org/gitlab-ui';
import { convertPermissionToBoolean } from '~/lib/utils/common_utils';
import Icon from '~/vue_shared/components/icon.vue'; import Icon from '~/vue_shared/components/icon.vue';
import FileRow from '~/vue_shared/components/file_row.vue'; import FileRow from '~/vue_shared/components/file_row.vue';
import FileRowStats from './file_row_stats.vue'; import FileRowStats from './file_row_stats.vue';
const treeListStorageKey = 'mr_diff_tree_list';
export default { export default {
directives: {
Tooltip,
},
components: { components: {
Icon, Icon,
FileRow, FileRow,
}, },
data() { data() {
const treeListStored = localStorage.getItem(treeListStorageKey);
const renderTreeList = treeListStored !== null ?
convertPermissionToBoolean(treeListStored) : true;
return { return {
search: '', search: '',
renderTreeList,
focusSearch: false,
}; };
}, },
computed: { computed: {
...@@ -20,15 +33,35 @@ export default { ...@@ -20,15 +33,35 @@ export default {
filteredTreeList() { filteredTreeList() {
const search = this.search.toLowerCase().trim(); const search = this.search.toLowerCase().trim();
if (search === '') return this.tree; if (search === '') return this.renderTreeList ? this.tree : this.allBlobs;
return this.allBlobs.filter(f => f.name.toLowerCase().indexOf(search) >= 0); return this.allBlobs.filter(f => f.name.toLowerCase().indexOf(search) >= 0);
}, },
rowDisplayTextKey() {
if (this.renderTreeList && this.search.trim() === '') {
return 'name';
}
return 'path';
},
}, },
methods: { methods: {
...mapActions('diffs', ['toggleTreeOpen', 'scrollToFile']), ...mapActions('diffs', ['toggleTreeOpen', 'scrollToFile']),
clearSearch() { clearSearch() {
this.search = ''; this.search = '';
this.toggleFocusSearch(false);
},
toggleRenderTreeList(toggle) {
this.renderTreeList = toggle;
localStorage.setItem(treeListStorageKey, this.renderTreeList);
},
toggleFocusSearch(toggle) {
this.focusSearch = toggle;
},
blurSearch() {
if (this.search.trim() === '') {
this.toggleFocusSearch(false);
}
}, },
}, },
FileRowStats, FileRowStats,
...@@ -37,28 +70,67 @@ export default { ...@@ -37,28 +70,67 @@ export default {
<template> <template>
<div class="tree-list-holder d-flex flex-column"> <div class="tree-list-holder d-flex flex-column">
<div class="append-bottom-8 position-relative tree-list-search"> <div class="append-bottom-8 position-relative tree-list-search d-flex">
<icon <div class="flex-fill d-flex">
name="search"
class="position-absolute tree-list-icon"
/>
<input
v-model="search"
:placeholder="s__('MergeRequest|Filter files')"
type="search"
class="form-control"
/>
<button
v-show="search"
:aria-label="__('Clear search')"
type="button"
class="position-absolute tree-list-icon tree-list-clear-icon border-0 p-0"
@click="clearSearch"
>
<icon <icon
name="close" name="search"
class="position-absolute tree-list-icon"
/>
<input
v-model="search"
:placeholder="s__('MergeRequest|Filter files')"
type="search"
class="form-control"
@focus="toggleFocusSearch(true)"
@blur="blurSearch"
/> />
</button> <button
v-show="search"
:aria-label="__('Clear search')"
type="button"
class="position-absolute bg-transparent tree-list-icon tree-list-clear-icon border-0 p-0"
@click="clearSearch"
>
<icon
name="close"
/>
</button>
</div>
<div
v-show="!focusSearch"
class="btn-group prepend-left-8 tree-list-view-toggle"
>
<button
v-tooltip.hover
:aria-label="__('List view')"
:title="__('List view')"
:class="{
active: !renderTreeList
}"
class="btn btn-default pt-0 pb-0 d-flex align-items-center"
type="button"
@click="toggleRenderTreeList(false)"
>
<icon
name="hamburger"
/>
</button>
<button
v-tooltip.hover
:aria-label="__('Tree view')"
:title="__('Tree view')"
:class="{
active: renderTreeList
}"
class="btn btn-default pt-0 pb-0 d-flex align-items-center"
type="button"
@click="toggleRenderTreeList(true)"
>
<icon
name="file-tree"
/>
</button>
</div>
</div> </div>
<div <div
class="tree-list-scroll" class="tree-list-scroll"
...@@ -72,6 +144,8 @@ export default { ...@@ -72,6 +144,8 @@ export default {
:hide-extra-on-tree="true" :hide-extra-on-tree="true"
:extra-component="$options.FileRowStats" :extra-component="$options.FileRowStats"
:show-changed-icon="true" :show-changed-icon="true"
:display-text-key="rowDisplayTextKey"
:should-truncate-start="true"
@toggleTreeOpen="toggleTreeOpen" @toggleTreeOpen="toggleTreeOpen"
@clickFile="scrollToFile" @clickFile="scrollToFile"
/> />
......
<script> <script>
import _ from 'underscore';
import CiIcon from '~/vue_shared/components/ci_icon.vue'; import CiIcon from '~/vue_shared/components/ci_icon.vue';
import Icon from '~/vue_shared/components/icon.vue'; import Icon from '~/vue_shared/components/icon.vue';
import tooltip from '~/vue_shared/directives/tooltip'; import tooltip from '~/vue_shared/directives/tooltip';
...@@ -9,11 +8,9 @@ export default { ...@@ -9,11 +8,9 @@ export default {
CiIcon, CiIcon,
Icon, Icon,
}, },
directives: { directives: {
tooltip, tooltip,
}, },
props: { props: {
job: { job: {
type: Object, type: Object,
...@@ -24,10 +21,9 @@ export default { ...@@ -24,10 +21,9 @@ export default {
required: true, required: true,
}, },
}, },
computed: { computed: {
tooltipText() { tooltipText() {
return `${_.escape(this.job.name)} - ${this.job.status.tooltip}`; return `${this.job.name} - ${this.job.status.tooltip}`;
}, },
}, },
}; };
...@@ -36,7 +32,10 @@ export default { ...@@ -36,7 +32,10 @@ export default {
<template> <template>
<div <div
class="build-job" class="build-job"
:class="{ retried: job.retried, active: isActive }" :class="{
retried: job.retried,
active: isActive
}"
> >
<a <a
v-tooltip v-tooltip
......
...@@ -7,14 +7,21 @@ const ENDLESS_SCROLL_BOTTOM_PX = 400; ...@@ -7,14 +7,21 @@ const ENDLESS_SCROLL_BOTTOM_PX = 400;
const ENDLESS_SCROLL_FIRE_DELAY_MS = 1000; const ENDLESS_SCROLL_FIRE_DELAY_MS = 1000;
export default { export default {
init(limit = 0, preload = false, disable = false, prepareData = $.noop, callback = $.noop) { init(
limit = 0,
preload = false,
disable = false,
prepareData = $.noop,
callback = $.noop,
container = '',
) {
this.url = $('.content_list').data('href') || removeParams(['limit', 'offset']); this.url = $('.content_list').data('href') || removeParams(['limit', 'offset']);
this.limit = limit; this.limit = limit;
this.offset = parseInt(getParameterByName('offset'), 10) || this.limit; this.offset = parseInt(getParameterByName('offset'), 10) || this.limit;
this.disable = disable; this.disable = disable;
this.prepareData = prepareData; this.prepareData = prepareData;
this.callback = callback; this.callback = callback;
this.loading = $('.loading').first(); this.loading = $(`${container} .loading`).first();
if (preload) { if (preload) {
this.offset = 0; this.offset = 0;
this.getOld(); this.getOld();
......
...@@ -170,7 +170,7 @@ export default class UserTabs { ...@@ -170,7 +170,7 @@ export default class UserTabs {
this.loadActivityCalendar('activity'); this.loadActivityCalendar('activity');
// eslint-disable-next-line no-new // eslint-disable-next-line no-new
new Activities(); new Activities('#activity');
this.loaded.activity = true; this.loaded.activity = true;
} }
......
...@@ -34,10 +34,21 @@ export default { ...@@ -34,10 +34,21 @@ export default {
required: false, required: false,
default: false, default: false,
}, },
displayTextKey: {
type: String,
required: false,
default: 'name',
},
shouldTruncateStart: {
type: Boolean,
required: false,
default: false,
},
}, },
data() { data() {
return { return {
mouseOver: false, mouseOver: false,
truncateStart: 0,
}; };
}, },
computed: { computed: {
...@@ -60,6 +71,15 @@ export default { ...@@ -60,6 +71,15 @@ export default {
'is-open': this.file.opened, 'is-open': this.file.opened,
}; };
}, },
outputText() {
const text = this.file[this.displayTextKey];
if (this.truncateStart === 0) {
return text;
}
return `...${text.substring(this.truncateStart, text.length)}`;
},
}, },
watch: { watch: {
'file.active': function fileActiveWatch(active) { 'file.active': function fileActiveWatch(active) {
...@@ -72,6 +92,15 @@ export default { ...@@ -72,6 +92,15 @@ export default {
if (this.hasPathAtCurrentRoute()) { if (this.hasPathAtCurrentRoute()) {
this.scrollIntoView(true); this.scrollIntoView(true);
} }
if (this.shouldTruncateStart) {
const { scrollWidth, offsetWidth } = this.$refs.textOutput;
const textOverflow = scrollWidth - offsetWidth;
if (textOverflow > 0) {
this.truncateStart = Math.ceil(textOverflow / 5) + 3;
}
}
}, },
methods: { methods: {
toggleTreeOpen(path) { toggleTreeOpen(path) {
...@@ -139,6 +168,7 @@ export default { ...@@ -139,6 +168,7 @@ export default {
class="file-row-name-container" class="file-row-name-container"
> >
<span <span
ref="textOutput"
:style="levelIndentation" :style="levelIndentation"
class="file-row-name str-truncated" class="file-row-name str-truncated"
> >
...@@ -156,7 +186,7 @@ export default { ...@@ -156,7 +186,7 @@ export default {
:size="16" :size="16"
class="append-right-5" class="append-right-5"
/> />
{{ file.name }} {{ outputText }}
</span> </span>
<component <component
:is="extraComponent" :is="extraComponent"
...@@ -175,6 +205,8 @@ export default { ...@@ -175,6 +205,8 @@ export default {
:hide-extra-on-tree="hideExtraOnTree" :hide-extra-on-tree="hideExtraOnTree"
:extra-component="extraComponent" :extra-component="extraComponent"
:show-changed-icon="showChangedIcon" :show-changed-icon="showChangedIcon"
:display-text-key="displayTextKey"
:should-truncate-start="shouldTruncateStart"
@toggleTreeOpen="toggleTreeOpen" @toggleTreeOpen="toggleTreeOpen"
@clickFile="clickedFile" @clickFile="clickedFile"
/> />
......
...@@ -334,6 +334,14 @@ img.emoji { ...@@ -334,6 +334,14 @@ img.emoji {
} }
} }
.outline-0 {
outline: 0;
&:focus {
outline: 0;
}
}
/** COMMON CLASSES **/ /** COMMON CLASSES **/
.prepend-top-0 { margin-top: 0; } .prepend-top-0 { margin-top: 0; }
.prepend-top-2 { margin-top: 2px; } .prepend-top-2 { margin-top: 2px; }
...@@ -373,3 +381,5 @@ img.emoji { ...@@ -373,3 +381,5 @@ img.emoji {
.flex-align-self-center { align-self: center; } .flex-align-self-center { align-self: center; }
.flex-grow { flex-grow: 1; } .flex-grow { flex-grow: 1; }
.flex-no-shrink { flex-shrink: 0; } .flex-no-shrink { flex-shrink: 0; }
.mw-460 { max-width: 460px; }
.ws-initial { white-space: initial; }
...@@ -37,6 +37,7 @@ ...@@ -37,6 +37,7 @@
button { button {
padding-top: 0; padding-top: 0;
background-color: transparent;
} }
&.active a, &.active a,
......
...@@ -1027,8 +1027,12 @@ ...@@ -1027,8 +1027,12 @@
overflow-x: auto; overflow-x: auto;
} }
.tree-list-search .form-control { .tree-list-search {
padding-left: 30px; flex: 0 0 34px;
.form-control {
padding-left: 30px;
}
} }
.tree-list-icon { .tree-list-icon {
...@@ -1063,3 +1067,9 @@ ...@@ -1063,3 +1067,9 @@
} }
} }
} }
.tree-list-view-toggle {
svg {
top: 0;
}
}
# frozen_string_literal: true # frozen_string_literal: true
module GroupsHelper module GroupsHelper
<<<<<<< HEAD
prepend EE::GroupsHelper prepend EE::GroupsHelper
=======
>>>>>>> upstream/master
def group_overview_nav_link_paths def group_overview_nav_link_paths
%w[ %w[
groups#show groups#show
......
...@@ -8,7 +8,10 @@ ...@@ -8,7 +8,10 @@
= render "layouts/header/ee_license_banner" = render "layouts/header/ee_license_banner"
= render "layouts/broadcast" = render "layouts/broadcast"
= render "layouts/header/read_only_banner" = render "layouts/header/read_only_banner"
<<<<<<< HEAD
= render "layouts/nav/ee/classification_level_banner" = render "layouts/nav/ee/classification_level_banner"
=======
>>>>>>> upstream/master
= yield :flash_message = yield :flash_message
= render "shared/ping_consent" = render "shared/ping_consent"
- unless @hide_breadcrumbs - unless @hide_breadcrumbs
......
---
title: Remove duplicate escape in job sidebar
merge_request:
author:
type: fixed
title: Adds container to pager to enable scoping
merge_request: 22529
? author
type: other
---
title: Add transparent background to markdown header tabs
merge_request: 22565
author: George Tsiolis
type: fixed
---
title: Switch between tree list & file list in diffs file browser
merge_request: 22191
author:
type: added
# frozen_string_literal: true
NO_SPECS_LABELS = %w[backstage Documentation QA].freeze NO_SPECS_LABELS = %w[backstage Documentation QA].freeze
NO_NEW_SPEC_MESSAGE = <<~MSG.freeze NO_NEW_SPEC_MESSAGE = <<~MSG.freeze
You've made some app changes, but didn't add any tests. You've made some app changes, but didn't add any tests.
...@@ -9,8 +11,8 @@ def presented_no_changelog_labels ...@@ -9,8 +11,8 @@ def presented_no_changelog_labels
NO_SPECS_LABELS.map { |label| "~#{label}" }.join(', ') NO_SPECS_LABELS.map { |label| "~#{label}" }.join(', ')
end end
has_app_changes = !git.modified_files.grep(%r{\A(ee/)?(app|lib|db/(geo/)?(post_)?migrate)/}).empty? has_app_changes = !helper.all_changed_files.grep(%r{\A(ee/)?(app|lib|db/(geo/)?(post_)?migrate)/}).empty?
has_spec_changes = !git.modified_files.grep(%r{\A(ee/)?spec/}).empty? has_spec_changes = !helper.all_changed_files.grep(%r{\A(ee/)?spec/}).empty?
new_specs_needed = (gitlab.mr_labels & NO_SPECS_LABELS).empty? new_specs_needed = (gitlab.mr_labels & NO_SPECS_LABELS).empty?
if has_app_changes && !has_spec_changes && new_specs_needed if has_app_changes && !has_spec_changes && new_specs_needed
......
...@@ -242,6 +242,33 @@ verification requirement. Navigate to `Admin area ➔ Settings` and uncheck ...@@ -242,6 +242,33 @@ verification requirement. Navigate to `Admin area ➔ Settings` and uncheck
**Require users to prove ownership of custom domains** in the Pages section. **Require users to prove ownership of custom domains** in the Pages section.
This setting is enabled by default. This setting is enabled by default.
### Access control
Access control was [introduced](https://gitlab.com/gitlab-org/gitlab-ce/issues/33422)
in GitLab 11.5. It can be configured per-project, and allows access to a Pages
site to be controlled based on a user's membership to that project.
Access control works by registering the Pages daemon as an OAuth application
with GitLab. Whenever a request to access a private Pages site is made by an
unauthenticated user, the Pages daemon redirects the user to GitLab. If
authentication is successful, the user is redirected back to Pages with a token,
which is persisted in a cookie. The cookies are signed with a secret key, so
tampering can be detected.
Each request to view a resource in a private site is authenticated by Pages
using that token. For each request it receives, it makes a request to the GitLab
API to check that the user is authorized to read that site.
Pages access control is currently disabled by default. To enable it, you must:
1. Enable it in `/etc/gitlab/gitlab.rb`
```ruby
gitlab_pages['access_control'] = true
```
1. [Reconfigure GitLab][reconfigure]
## Activate verbose logging for daemon ## Activate verbose logging for daemon
Verbose logging was [introduced](https://gitlab.com/gitlab-org/omnibus-gitlab/merge_requests/2533) in Verbose logging was [introduced](https://gitlab.com/gitlab-org/omnibus-gitlab/merge_requests/2533) in
......
...@@ -391,6 +391,44 @@ the first one with a backslash (\). For example `pages.example.io` would be: ...@@ -391,6 +391,44 @@ the first one with a backslash (\). For example `pages.example.io` would be:
server_name ~^.*\.pages\.example\.io$; server_name ~^.*\.pages\.example\.io$;
``` ```
## Access control
Access control was [introduced](https://gitlab.com/gitlab-org/gitlab-ce/issues/33422)
in GitLab 11.5. It can be configured per-project, and allows access to a Pages
site to be controlled based on a user's membership to that project.
Access control works by registering the Pages daemon as an OAuth application
with GitLab. Whenever a request to access a private Pages site is made by an
unauthenticated user, the Pages daemon redirects the user to GitLab. If
authentication is successful, the user is redirected back to Pages with a token,
which is persisted in a cookie. The cookies are signed with a secret key, so
tampering can be detected.
Each request to view a resource in a private site is authenticated by Pages
using that token. For each request it receives, it makes a request to the GitLab
API to check that the user is authorized to read that site.
Pages access control is currently disabled by default. To enable it, you must:
1. Modify your `config/gitlab.yml` file:
```yaml
pages:
access_control: true
```
1. [Restart GitLab][restart]
1. Create a new [system OAuth application](../../integration/oauth_provider.md#adding-an-application-through-the-profile)
This should be called `GitLab Pages` and have a `Redirect URL` of
`https://projects.example.io/auth`. It does not need to be a "trusted"
application, but it does need the "api" scope.
1. Start the Pages daemon with the following additional arguments:
```shell
-auth-client-secret <OAuth code generated by GitLab> \
-auth-redirect-uri http://projects.example.io/auth \
-auth-secret <40 random hex characters> \
-auth-server <URL of the GitLab instance>
```
## Change storage path ## Change storage path
Follow the steps below to change the default path where GitLab Pages' contents Follow the steps below to change the default path where GitLab Pages' contents
......
...@@ -312,7 +312,7 @@ We're always looking for contributions that can mitigate these ...@@ -312,7 +312,7 @@ We're always looking for contributions that can mitigate these
If you think that registration token for a Project was revealed, you should If you think that registration token for a Project was revealed, you should
reset them. It's recommended because such token can be used to register another reset them. It's recommended because such token can be used to register another
Runner to thi Project. It may be next used to obtain the values of secret Runner to the Project. It may be next used to obtain the values of secret
variables or clone the project code, that normally may be unavailable for the variables or clone the project code, that normally may be unavailable for the
attacker. attacker.
......
...@@ -2032,4 +2032,8 @@ CI with various languages. ...@@ -2032,4 +2032,8 @@ CI with various languages.
[schedules]: ../../user/project/pipelines/schedules.md [schedules]: ../../user/project/pipelines/schedules.md
[variables-expressions]: ../variables/README.md#variables-expressions [variables-expressions]: ../variables/README.md#variables-expressions
[ee]: https://about.gitlab.com/gitlab-ee/ [ee]: https://about.gitlab.com/gitlab-ee/
<<<<<<< HEAD
[gitlab-versions]: https://about.gitlab.com/products/ [gitlab-versions]: https://about.gitlab.com/products/
=======
[gitlab-versions]: https://about.gitlab.com/products/
>>>>>>> upstream/master
...@@ -112,3 +112,8 @@ feature flag. You can stub a feature flag as follows: ...@@ -112,3 +112,8 @@ feature flag. You can stub a feature flag as follows:
```ruby ```ruby
stub_feature_flags(my_feature_flag: false) stub_feature_flags(my_feature_flag: false)
``` ```
## Enabling a feature flag
Check how to [roll out changes using feature flags](rolling_out_changes_using_feature_flags.md).
...@@ -20,6 +20,7 @@ are very appreciative of the work done by translators and proofreaders! ...@@ -20,6 +20,7 @@ are very appreciative of the work done by translators and proofreaders!
- French - French
- Davy Defaud - [GitLab](https://gitlab.com/DevDef), [Crowdin](https://crowdin.com/profile/DevDef) - Davy Defaud - [GitLab](https://gitlab.com/DevDef), [Crowdin](https://crowdin.com/profile/DevDef)
- German - German
- Michael Hahnle - [GitLab](https://gitlab.com/mhah), [Crowdin](https://crowdin.com/profile/mhah)
- Indonesian - Indonesian
- Ahmad Naufal Mukhtar - [GitLab](https://gitlab.com/anaufalm), [Crowdin](https://crowdin.com/profile/anaufalm) - Ahmad Naufal Mukhtar - [GitLab](https://gitlab.com/anaufalm), [Crowdin](https://crowdin.com/profile/anaufalm)
- Italian - Italian
......
...@@ -320,7 +320,11 @@ created, and is uploaded as an artifact which you can later download and check ...@@ -320,7 +320,11 @@ created, and is uploaded as an artifact which you can later download and check
out. out.
Any differences between the source and target branches are also Any differences between the source and target branches are also
<<<<<<< HEAD
[shown in the merge request widget](../../user/project/merge_requests/code_quality.md). [shown in the merge request widget](../../user/project/merge_requests/code_quality.md).
=======
[shown in the merge request widget](https://docs.gitlab.com/ee/user/project/merge_requests/code_quality.html).
>>>>>>> upstream/master
### Auto SAST **[ULTIMATE]** ### Auto SAST **[ULTIMATE]**
...@@ -333,8 +337,15 @@ report is created, it's uploaded as an artifact which you can later download and ...@@ -333,8 +337,15 @@ report is created, it's uploaded as an artifact which you can later download and
check out. check out.
Any security warnings are also Any security warnings are also
<<<<<<< HEAD
[shown in the merge request widget](../../user/project/merge_requests/sast.md). [shown in the merge request widget](../../user/project/merge_requests/sast.md).
NOTE: **Note:**
The Auto SAST stage will be skipped on licenses other than Ultimate.
=======
[shown in the merge request widget](https://docs.gitlab.com/ee//user/project/merge_requests/sast.html).
>>>>>>> upstream/master
NOTE: **Note:** NOTE: **Note:**
The Auto SAST stage will be skipped on licenses other than Ultimate. The Auto SAST stage will be skipped on licenses other than Ultimate.
...@@ -354,6 +365,9 @@ Any security warnings are also ...@@ -354,6 +365,9 @@ Any security warnings are also
NOTE: **Note:** NOTE: **Note:**
The Auto Dependency Scanning stage will be skipped on licenses other than Ultimate. The Auto Dependency Scanning stage will be skipped on licenses other than Ultimate.
NOTE: **Note:**
The Auto Dependency Scanning stage will be skipped on licenses other than Ultimate.
### Auto License Management **[ULTIMATE]** ### Auto License Management **[ULTIMATE]**
> Introduced in [GitLab Ultimate][ee] 11.0. > Introduced in [GitLab Ultimate][ee] 11.0.
...@@ -370,6 +384,9 @@ Any licenses are also ...@@ -370,6 +384,9 @@ Any licenses are also
NOTE: **Note:** NOTE: **Note:**
The Auto License Management stage will be skipped on licenses other than Ultimate. The Auto License Management stage will be skipped on licenses other than Ultimate.
NOTE: **Note:**
The Auto License Management stage will be skipped on licenses other than Ultimate.
### Auto Container Scanning ### Auto Container Scanning
> Introduced in GitLab 10.4. > Introduced in GitLab 10.4.
......
...@@ -30,12 +30,12 @@ to learn more. ...@@ -30,12 +30,12 @@ to learn more.
## Delete merged branches ## Delete merged branches
> [Introduced][ce-6449] in GitLab 8.14. > [Introduced](https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/6449) in GitLab 8.14.
![Delete merged branches](img/delete_merged_branches.png) ![Delete merged branches](img/delete_merged_branches.png)
This feature allows merged branches to be deleted in bulk. Only branches that This feature allows merged branches to be deleted in bulk. Only branches that
have been merged and [are not protected][protected] will be deleted as part of have been merged and [are not protected](../../protected_branches.md) will be deleted as part of
this operation. this operation.
It's particularly useful to clean up old branches that were not deleted It's particularly useful to clean up old branches that were not deleted
...@@ -44,7 +44,7 @@ automatically when a merge request was merged. ...@@ -44,7 +44,7 @@ automatically when a merge request was merged.
## Branch filter search box ## Branch filter search box
> [Introduced][https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/22166] in GitLab 11.5. > [Introduced](https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/22166) in GitLab 11.5.
![Branch filter search box](img/branch_filter_search_box.png) ![Branch filter search box](img/branch_filter_search_box.png)
...@@ -57,6 +57,3 @@ Sometimes when you have hundreds of branches you may want a more flexible matchi ...@@ -57,6 +57,3 @@ Sometimes when you have hundreds of branches you may want a more flexible matchi
- `^feature` will only match branch names that begin with 'feature'. - `^feature` will only match branch names that begin with 'feature'.
- `feature$` will only match branch names that end with 'feature'. - `feature$` will only match branch names that end with 'feature'.
[ce-6449]: https://gitlab.com/gitlab-org/gitlab-ce/merge_requests/6449 "Add button to delete all merged branches"
[protected]: ../../protected_branches.md
...@@ -286,7 +286,7 @@ module Gitlab ...@@ -286,7 +286,7 @@ module Gitlab
end end
def patch_name_from_branch(branch_name) def patch_name_from_branch(branch_name)
branch_name.parameterize << '.patch' "#{branch_name.parameterize}.patch"
end end
def patch_url def patch_url
...@@ -434,9 +434,11 @@ module Gitlab ...@@ -434,9 +434,11 @@ module Gitlab
end end
def conflicting_files_msg def conflicting_files_msg
failed_files.reduce("The conflicts detected were as follows:\n") do |memo, file| header = "The conflicts detected were as follows:\n"
memo << "\n - #{file}" separator = "\n - "
end failed_items = failed_files.join(separator)
"#{header}#{separator}#{failed_items}"
end end
end end
end end
...@@ -4679,6 +4679,9 @@ msgstr "" ...@@ -4679,6 +4679,9 @@ msgstr ""
msgid "List available repositories" msgid "List available repositories"
msgstr "" msgstr ""
msgid "List view"
msgstr ""
msgid "List your Bitbucket Server repositories" msgid "List your Bitbucket Server repositories"
msgstr "" msgstr ""
...@@ -8280,6 +8283,7 @@ msgstr "" ...@@ -8280,6 +8283,7 @@ msgstr ""
msgid "Track time with quick actions" msgid "Track time with quick actions"
msgstr "" msgstr ""
<<<<<<< HEAD
msgid "Trending" msgid "Trending"
msgstr "" msgstr ""
...@@ -8287,6 +8291,12 @@ msgid "Trigger" ...@@ -8287,6 +8291,12 @@ msgid "Trigger"
msgstr "" msgstr ""
msgid "Trigger pipelines for mirror updates" msgid "Trigger pipelines for mirror updates"
=======
msgid "Tree view"
msgstr ""
msgid "Trending"
>>>>>>> upstream/master
msgstr "" msgstr ""
msgid "Trigger pipelines when branches or tags are updated from the upstream repository. Depending on the activity of the upstream repository, this may greatly increase the load on your CI runners. Only enable this if you know they can handle the load." msgid "Trigger pipelines when branches or tags are updated from the upstream repository. Depending on the activity of the upstream repository, this may greatly increase the load on your CI runners. Only enable this if you know they can handle the load."
......
...@@ -151,9 +151,8 @@ describe 'Jobs', :clean_gitlab_redis_shared_state do ...@@ -151,9 +151,8 @@ describe 'Jobs', :clean_gitlab_redis_shared_state do
end end
it 'renders escaped tooltip name' do it 'renders escaped tooltip name' do
page.within('aside.right-sidebar') do page.find('.active.build-job a').hover
expect(find('.active.build-job a')['data-original-title']).to eq('&lt;img src=x onerror=alert(document.domain)&gt; - passed') expect(page).to have_content('<img src=x onerror=alert(document.domain)> - passed')
end
end end
end end
......
...@@ -53,7 +53,7 @@ describe('Diffs tree list component', () => { ...@@ -53,7 +53,7 @@ describe('Diffs tree list component', () => {
fileHash: 'test', fileHash: 'test',
key: 'index.js', key: 'index.js',
name: 'index.js', name: 'index.js',
path: 'index.js', path: 'app/index.js',
removedLines: 0, removedLines: 0,
tempFile: true, tempFile: true,
type: 'blob', type: 'blob',
...@@ -104,7 +104,55 @@ describe('Diffs tree list component', () => { ...@@ -104,7 +104,55 @@ describe('Diffs tree list component', () => {
vm.$el.querySelector('.file-row').click(); vm.$el.querySelector('.file-row').click();
expect(vm.$store.dispatch).toHaveBeenCalledWith('diffs/scrollToFile', 'index.js'); expect(vm.$store.dispatch).toHaveBeenCalledWith('diffs/scrollToFile', 'app/index.js');
});
it('renders as file list when renderTreeList is false', done => {
vm.renderTreeList = false;
vm.$nextTick(() => {
expect(vm.$el.querySelectorAll('.file-row').length).toBe(1);
done();
});
});
it('renders file paths when renderTreeList is false', done => {
vm.renderTreeList = false;
vm.$nextTick(() => {
expect(vm.$el.querySelector('.file-row').textContent).toContain('app/index.js');
done();
});
});
it('hides render buttons when input is focused', done => {
const focusEvent = new Event('focus');
vm.$el.querySelector('.form-control').dispatchEvent(focusEvent);
vm.$nextTick(() => {
expect(vm.$el.querySelector('.tree-list-view-toggle').style.display).toBe('none');
done();
});
});
it('shows render buttons when input is blurred', done => {
const blurEvent = new Event('blur');
vm.focusSearch = true;
vm.$nextTick()
.then(() => {
vm.$el.querySelector('.form-control').dispatchEvent(blurEvent);
})
.then(vm.$nextTick)
.then(() => {
expect(vm.$el.querySelector('.tree-list-view-toggle').style.display).not.toBe('none');
})
.then(done)
.catch(done.fail);
}); });
}); });
...@@ -117,4 +165,24 @@ describe('Diffs tree list component', () => { ...@@ -117,4 +165,24 @@ describe('Diffs tree list component', () => {
expect(vm.search).toBe(''); expect(vm.search).toBe('');
}); });
}); });
describe('toggleRenderTreeList', () => {
it('updates renderTreeList', () => {
expect(vm.renderTreeList).toBe(true);
vm.toggleRenderTreeList(false);
expect(vm.renderTreeList).toBe(false);
});
});
describe('toggleFocusSearch', () => {
it('updates focusSearch', () => {
expect(vm.focusSearch).toBe(false);
vm.toggleFocusSearch(true);
expect(vm.focusSearch).toBe(true);
});
});
}); });
...@@ -444,6 +444,14 @@ describe('DiffsStoreUtils', () => { ...@@ -444,6 +444,14 @@ describe('DiffsStoreUtils', () => {
addedLines: 0, addedLines: 0,
fileHash: 'test', fileHash: 'test',
}, },
{
newPath: 'app/test/filepathneedstruncating.js',
deletedFile: false,
newFile: true,
removedLines: 0,
addedLines: 0,
fileHash: 'test',
},
{ {
newPath: 'package.json', newPath: 'package.json',
deletedFile: true, deletedFile: true,
...@@ -498,6 +506,19 @@ describe('DiffsStoreUtils', () => { ...@@ -498,6 +506,19 @@ describe('DiffsStoreUtils', () => {
type: 'blob', type: 'blob',
tree: [], tree: [],
}, },
{
addedLines: 0,
changed: true,
deleted: false,
fileHash: 'test',
key: 'app/test/filepathneedstruncating.js',
name: 'filepathneedstruncating.js',
path: 'app/test/filepathneedstruncating.js',
removedLines: 0,
tempFile: true,
type: 'blob',
tree: [],
},
], ],
}, },
], ],
...@@ -527,6 +548,7 @@ describe('DiffsStoreUtils', () => { ...@@ -527,6 +548,7 @@ describe('DiffsStoreUtils', () => {
'app/index.js', 'app/index.js',
'app/test', 'app/test',
'app/test/index.js', 'app/test/index.js',
'app/test/filepathneedstruncating.js',
'package.json', 'package.json',
]); ]);
}); });
......
...@@ -71,4 +71,40 @@ describe('RepoFile', () => { ...@@ -71,4 +71,40 @@ describe('RepoFile', () => {
expect(vm.$el.querySelector('.file-row-name').style.marginLeft).toBe('32px'); expect(vm.$el.querySelector('.file-row-name').style.marginLeft).toBe('32px');
}); });
describe('outputText', () => {
beforeEach(done => {
createComponent({
file: {
...file(),
path: 'app/assets/index.js',
},
level: 0,
});
vm.displayTextKey = 'path';
vm.$nextTick(done);
});
it('returns text if truncateStart is 0', done => {
vm.truncateStart = 0;
vm.$nextTick(() => {
expect(vm.outputText).toBe('app/assets/index.js');
done();
});
});
it('returns text truncated at start', done => {
vm.truncateStart = 5;
vm.$nextTick(() => {
expect(vm.outputText).toBe('...ssets/index.js');
done();
});
});
});
}); });
...@@ -616,11 +616,16 @@ ...@@ -616,11 +616,16 @@
lodash "^4.17.10" lodash "^4.17.10"
to-fast-properties "^2.0.0" to-fast-properties "^2.0.0"
"@gitlab-org/gitlab-svgs@^1.23.0", "@gitlab-org/gitlab-svgs@^1.32.0": "@gitlab-org/gitlab-svgs@^1.23.0":
version "1.32.0" version "1.32.0"
resolved "https://registry.yarnpkg.com/@gitlab-org/gitlab-svgs/-/gitlab-svgs-1.32.0.tgz#a65ab7724fa7d55be8e5cc9b2dbe3f0757432fd3" resolved "https://registry.yarnpkg.com/@gitlab-org/gitlab-svgs/-/gitlab-svgs-1.32.0.tgz#a65ab7724fa7d55be8e5cc9b2dbe3f0757432fd3"
integrity sha512-L3o8dFUd2nSkVZBwh2hCJWzNzADJ3dTBZxamND8NLosZK9/ohNhccmsQOZGyMCUHaOzm4vifaaXkAXh04UtMKA== integrity sha512-L3o8dFUd2nSkVZBwh2hCJWzNzADJ3dTBZxamND8NLosZK9/ohNhccmsQOZGyMCUHaOzm4vifaaXkAXh04UtMKA==
"@gitlab-org/gitlab-svgs@^1.33.0":
version "1.33.0"
resolved "https://registry.yarnpkg.com/@gitlab-org/gitlab-svgs/-/gitlab-svgs-1.33.0.tgz#068566e8ee00795f6f09f58236f08e1716f9f04a"
integrity sha512-8ajtUHk6gQ1xosL/CO5IzHSFM/t18hx5pfzQ3cd0VuQXcyR6QKGuXTLwbYdmJDYOw1Etoo5DqDWxPEClHyZpiA==
"@gitlab-org/gitlab-ui@^1.8.0": "@gitlab-org/gitlab-ui@^1.8.0":
version "1.8.0" version "1.8.0"
resolved "https://registry.yarnpkg.com/@gitlab-org/gitlab-ui/-/gitlab-ui-1.8.0.tgz#dee33d78f68c91644273dbd51734b796108263ee" resolved "https://registry.yarnpkg.com/@gitlab-org/gitlab-ui/-/gitlab-ui-1.8.0.tgz#dee33d78f68c91644273dbd51734b796108263ee"
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment