Add latest changes from gitlab-org/gitlab@master
This commit is contained in:
parent
86461e8c72
commit
07f40d55ab
13 changed files with 107 additions and 40 deletions
|
@ -45,6 +45,7 @@ export default {
|
|||
'initialActiveAccessTokens',
|
||||
'noActiveTokensMessage',
|
||||
'showRole',
|
||||
'information',
|
||||
],
|
||||
data() {
|
||||
return {
|
||||
|
@ -100,6 +101,10 @@ export default {
|
|||
<hr />
|
||||
<h5>{{ header }}</h5>
|
||||
|
||||
<p v-if="information" data-testid="information-section">
|
||||
{{ information }}
|
||||
</p>
|
||||
|
||||
<gl-table
|
||||
data-testid="active-tokens"
|
||||
:empty-text="noActiveTokensMessage"
|
||||
|
|
|
@ -20,6 +20,7 @@ export const initAccessTokenTableApp = () => {
|
|||
const {
|
||||
accessTokenType,
|
||||
accessTokenTypePlural,
|
||||
information,
|
||||
initialActiveAccessTokens: initialActiveAccessTokensJson,
|
||||
noActiveTokensMessage: noTokensMessage,
|
||||
} = el.dataset;
|
||||
|
@ -43,6 +44,7 @@ export const initAccessTokenTableApp = () => {
|
|||
provide: {
|
||||
accessTokenType,
|
||||
accessTokenTypePlural,
|
||||
information,
|
||||
initialActiveAccessTokens,
|
||||
noActiveTokensMessage,
|
||||
showRole,
|
||||
|
|
|
@ -14,11 +14,10 @@ class Admin::ImpersonationTokensController < Admin::ApplicationController
|
|||
@impersonation_token = finder.build(impersonation_token_params)
|
||||
|
||||
if @impersonation_token.save
|
||||
PersonalAccessToken.redis_store!(current_user.id, @impersonation_token.token)
|
||||
redirect_to admin_user_impersonation_tokens_path, notice: _("A new impersonation token has been created.")
|
||||
render json: { new_token: @impersonation_token.token,
|
||||
active_access_tokens: active_impersonation_tokens }, status: :ok
|
||||
else
|
||||
set_index_vars
|
||||
render :index
|
||||
render json: { errors: @impersonation_token.errors.full_messages }, status: :unprocessable_entity
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -50,19 +49,19 @@ class Admin::ImpersonationTokensController < Admin::ApplicationController
|
|||
PersonalAccessTokensFinder.new({ user: user, impersonation: true }.merge(options))
|
||||
end
|
||||
|
||||
def active_impersonation_tokens
|
||||
tokens = finder(state: 'active', sort: 'expires_at_asc_id_desc').execute
|
||||
::ImpersonationAccessTokenSerializer.new.represent(tokens)
|
||||
end
|
||||
|
||||
def impersonation_token_params
|
||||
params.require(:personal_access_token).permit(:name, :expires_at, :impersonation, scopes: [])
|
||||
end
|
||||
|
||||
# rubocop: disable CodeReuse/ActiveRecord
|
||||
def set_index_vars
|
||||
@scopes = Gitlab::Auth.available_scopes_for(current_user)
|
||||
|
||||
@impersonation_token ||= finder.build
|
||||
@inactive_impersonation_tokens = finder(state: 'inactive').execute
|
||||
@active_impersonation_tokens = finder(state: 'active').execute.order(:expires_at)
|
||||
|
||||
@new_impersonation_token = PersonalAccessToken.redis_getdel(current_user.id)
|
||||
@active_impersonation_tokens = active_impersonation_tokens
|
||||
end
|
||||
# rubocop: enable CodeReuse/ActiveRecord
|
||||
end
|
||||
|
|
|
@ -8,12 +8,10 @@
|
|||
|
||||
.row.gl-mt-3
|
||||
.col-lg-12
|
||||
- if @new_impersonation_token
|
||||
= render 'shared/access_tokens/created_container',
|
||||
type: type,
|
||||
new_token_value: @new_impersonation_token
|
||||
#js-new-access-token-app{ data: { access_token_type: type } }
|
||||
|
||||
= render 'shared/access_tokens/form',
|
||||
ajax: true,
|
||||
type: type,
|
||||
title: _('Add an impersonation token'),
|
||||
path: admin_user_impersonation_tokens_path,
|
||||
|
@ -22,9 +20,4 @@
|
|||
scopes: @scopes,
|
||||
help_path: help_page_path('api/index', anchor: 'impersonation-tokens')
|
||||
|
||||
= render 'shared/access_tokens/table',
|
||||
type: type,
|
||||
type_plural: type_plural,
|
||||
impersonation: true,
|
||||
active_tokens: @active_impersonation_tokens,
|
||||
revoke_route_helper: ->(token) { revoke_admin_user_impersonation_token_path(token.user, token) }
|
||||
#js-access-token-table-app{ data: { access_token_type: type, access_token_type_plural: type_plural, initial_active_access_tokens: @active_impersonation_tokens.to_json, information: _("To see all the user's personal access tokens you must impersonate them first.") } }
|
||||
|
|
|
@ -169,6 +169,16 @@ A grace period can safely be lifted as soon as there are no warnings for 2 weeks
|
|||
1. Create an issue to fix TODOs and encourage Community contributions (via ~"good for new contributors" and/or ~"Seeking community contributions"). [See some examples](https://gitlab.com/gitlab-org/gitlab/-/issues/?sort=created_date&state=opened&label_name%5B%5D=good%20for%20new%20contributors&label_name%5B%5D=static%20code%20analysis&first_page_size=20).
|
||||
1. Create an issue to remove "grace period" after 2 weeks silence in `#f_rubocop` Slack channel. ([See an example](https://gitlab.com/gitlab-org/gitlab/-/issues/374903).)
|
||||
|
||||
### Silenced offenses
|
||||
|
||||
When offenses are silenced for cops in ["grace period"](#cop-grace-period),
|
||||
the `#f_rubocop` Slack channel receives a notification message every two hours.
|
||||
|
||||
To fix this issue:
|
||||
|
||||
1. Find cops with silenced offenses in the linked CI job.
|
||||
1. [Generate TODOs](../rake_tasks.md#generate-initial-rubocop-todo-list) for these cops.
|
||||
|
||||
#### RuboCop node pattern
|
||||
|
||||
When creating [node patterns](https://docs.rubocop.org/rubocop-ast/node_pattern.html) to match
|
||||
|
|
|
@ -1676,9 +1676,6 @@ msgstr ""
|
|||
msgid "A new email address has been added to your GitLab account: %{email}"
|
||||
msgstr ""
|
||||
|
||||
msgid "A new impersonation token has been created."
|
||||
msgstr ""
|
||||
|
||||
msgid "A new personal access token has been created"
|
||||
msgstr ""
|
||||
|
||||
|
|
|
@ -66,7 +66,13 @@ module RuboCop
|
|||
end
|
||||
|
||||
channel = 'f_rubocop'
|
||||
message = ":warning: `#{job_name}` passed :green: but contained silenced offenses. See #{job_url}"
|
||||
message = format(
|
||||
':warning: `%{job_name}` passed :green: but contained <%{job_url}|silenced offenses>. ' \
|
||||
'See <%{docs_link}|docs>.',
|
||||
docs_link: 'https://docs.gitlab.com/ee/development/contributing/style_guides.html#silenced-offenses',
|
||||
job_name: job_name,
|
||||
job_url: job_url)
|
||||
|
||||
emoji = 'rubocop'
|
||||
user_name = 'GitLab Bot'
|
||||
|
||||
|
|
|
@ -35,6 +35,10 @@ RSpec.describe Profiles::PersonalAccessTokensController do
|
|||
expect(created_token).not_to be_nil
|
||||
expect(created_token.expires_at).to eq(expires_at)
|
||||
end
|
||||
|
||||
it_behaves_like "#create access token" do
|
||||
let(:url) { :create }
|
||||
end
|
||||
end
|
||||
|
||||
describe '#index' do
|
||||
|
|
|
@ -9,15 +9,11 @@ RSpec.describe 'Admin > Users > Impersonation Tokens', :js do
|
|||
let!(:user) { create(:user) }
|
||||
|
||||
def active_impersonation_tokens
|
||||
find(".table.active-tokens")
|
||||
end
|
||||
|
||||
def no_personal_access_tokens_message
|
||||
find(".settings-message")
|
||||
find("[data-testid='active-tokens']")
|
||||
end
|
||||
|
||||
def created_impersonation_token
|
||||
find("#created-personal-access-token").value
|
||||
find_field('new-access-token').value
|
||||
end
|
||||
|
||||
before do
|
||||
|
@ -80,8 +76,7 @@ RSpec.describe 'Admin > Users > Impersonation Tokens', :js do
|
|||
|
||||
accept_gl_confirm(button_text: 'Revoke') { click_on "Revoke" }
|
||||
|
||||
expect(page).to have_selector(".settings-message")
|
||||
expect(no_personal_access_tokens_message).to have_text("This user has no active impersonation tokens.")
|
||||
expect(active_impersonation_tokens).to have_text("This user has no active impersonation tokens.")
|
||||
end
|
||||
|
||||
it "removes expired tokens from 'active' section" do
|
||||
|
@ -89,8 +84,7 @@ RSpec.describe 'Admin > Users > Impersonation Tokens', :js do
|
|||
|
||||
visit admin_user_impersonation_tokens_path(user_id: user.username)
|
||||
|
||||
expect(page).to have_selector(".settings-message")
|
||||
expect(no_personal_access_tokens_message).to have_text("This user has no active impersonation tokens.")
|
||||
expect(active_impersonation_tokens).to have_text("This user has no active impersonation tokens.")
|
||||
end
|
||||
end
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { GlButton, GlPagination, GlTable } from '@gitlab/ui';
|
||||
import { mount } from '@vue/test-utils';
|
||||
import { nextTick } from 'vue';
|
||||
import { mountExtended } from 'helpers/vue_test_utils_helper';
|
||||
import AccessTokenTableApp from '~/access_tokens/components/access_token_table_app.vue';
|
||||
import { EVENT_SUCCESS, PAGE_SIZE } from '~/access_tokens/components/constants';
|
||||
import { __, s__, sprintf } from '~/locale';
|
||||
|
@ -11,6 +11,7 @@ describe('~/access_tokens/components/access_token_table_app', () => {
|
|||
|
||||
const accessTokenType = 'personal access token';
|
||||
const accessTokenTypePlural = 'personal access tokens';
|
||||
const information = undefined;
|
||||
const initialActiveAccessTokens = [];
|
||||
const noActiveTokensMessage = 'This user has no active personal access tokens.';
|
||||
const showRole = false;
|
||||
|
@ -43,10 +44,11 @@ describe('~/access_tokens/components/access_token_table_app', () => {
|
|||
];
|
||||
|
||||
const createComponent = (props = {}) => {
|
||||
wrapper = mount(AccessTokenTableApp, {
|
||||
wrapper = mountExtended(AccessTokenTableApp, {
|
||||
provide: {
|
||||
accessTokenType,
|
||||
accessTokenTypePlural,
|
||||
information,
|
||||
initialActiveAccessTokens,
|
||||
noActiveTokensMessage,
|
||||
showRole,
|
||||
|
@ -101,6 +103,13 @@ describe('~/access_tokens/components/access_token_table_app', () => {
|
|||
);
|
||||
});
|
||||
|
||||
it('should render information section', () => {
|
||||
const info = 'This is my information';
|
||||
createComponent({ information: info });
|
||||
|
||||
expect(wrapper.findByTestId('information-section').text()).toBe(info);
|
||||
});
|
||||
|
||||
it('should render the `GlTable` component with default 6 column headers', () => {
|
||||
createComponent();
|
||||
|
||||
|
|
|
@ -35,4 +35,10 @@ RSpec.describe Admin::ImpersonationTokensController, :enable_admin_mode do
|
|||
expect(response).to have_gitlab_http_status(:not_found)
|
||||
end
|
||||
end
|
||||
|
||||
describe "#create" do
|
||||
it_behaves_like "#create access token" do
|
||||
let(:url) { admin_user_impersonation_tokens_path(user_id: user.username) }
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -62,25 +62,35 @@ RSpec.describe RuboCop::CheckGracefulTask do
|
|||
let(:adjusted_rubocop_status) { status_success }
|
||||
|
||||
context 'with sufficient environment variables' do
|
||||
let(:script) { 'scripts/slack' }
|
||||
let(:channel) { 'f_rubocop' }
|
||||
let(:emoji) { 'rubocop' }
|
||||
let(:user_name) { 'GitLab Bot' }
|
||||
let(:job_name) { 'some job name' }
|
||||
let(:job_url) { 'some job url' }
|
||||
let(:docs_link) { 'https://docs.gitlab.com/ee/development/contributing/style_guides.html#silenced-offenses' }
|
||||
|
||||
before do
|
||||
env = {
|
||||
'CI_SLACK_WEBHOOK_URL' => 'webhook_url',
|
||||
'CI_JOB_NAME' => 'job_name',
|
||||
'CI_JOB_URL' => 'job_url'
|
||||
'CI_JOB_NAME' => job_name,
|
||||
'CI_JOB_URL' => job_url
|
||||
}
|
||||
|
||||
stub_const('ENV', ENV.to_hash.update(env))
|
||||
end
|
||||
|
||||
it 'notifies slack' do
|
||||
popen_args = ['scripts/slack', channel, kind_of(String), 'rubocop', kind_of(String)]
|
||||
popen_result = ['', 0]
|
||||
expect(Gitlab::Popen).to receive(:popen).with(popen_args).and_return(popen_result)
|
||||
allow(Gitlab::Popen).to receive(:popen).with(anything).and_return(popen_result)
|
||||
|
||||
subject
|
||||
|
||||
message = a_kind_of(String).and include(job_name).and include(job_url).and include(docs_link)
|
||||
|
||||
expect(Gitlab::Popen).to have_received(:popen)
|
||||
.with([script, channel, message, emoji, user_name])
|
||||
|
||||
expect(output.string).to include("Notifying Slack ##{channel}.")
|
||||
end
|
||||
|
||||
|
|
|
@ -163,3 +163,35 @@ RSpec.shared_examples 'inactive resource access tokens' do |no_active_tokens_tex
|
|||
end
|
||||
end
|
||||
end
|
||||
|
||||
RSpec.shared_examples '#create access token' do
|
||||
let(:url) { {} }
|
||||
let_it_be(:admin) { create(:admin) }
|
||||
let_it_be(:token_attributes) { attributes_for(:personal_access_token) }
|
||||
|
||||
before do
|
||||
sign_in(admin)
|
||||
end
|
||||
|
||||
context "when POST is successful" do
|
||||
it "renders JSON with a new token" do
|
||||
post url, params: { personal_access_token: token_attributes }
|
||||
|
||||
parsed_body = Gitlab::Json.parse(response.body)
|
||||
expect(parsed_body['new_token']).not_to be_blank
|
||||
expect(parsed_body['errors']).to be_blank
|
||||
expect(response).to have_gitlab_http_status(:success)
|
||||
end
|
||||
end
|
||||
|
||||
context "when POST is unsuccessful" do
|
||||
it "renders JSON with an error" do
|
||||
post url, params: { personal_access_token: token_attributes.merge(scopes: []) }
|
||||
|
||||
parsed_body = Gitlab::Json.parse(response.body)
|
||||
expect(parsed_body['new_token']).to be_blank
|
||||
expect(parsed_body['errors']).not_to be_blank
|
||||
expect(response).to have_gitlab_http_status(:unprocessable_entity)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Reference in a new issue