mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 09:19:04 -04:00
# Backport This will backport the following commits from `main` to `8.11`: - [Adding user profiles tests for regular and serverless (#171554)](https://github.com/elastic/kibana/pull/171554) <!--- Backport version: 8.9.7 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sqren/backport) <!--BACKPORT [{"author":{"name":"Kurt","email":"kc13greiner@users.noreply.github.com"},"sourceCommit":{"committedDate":"2023-11-22T15:43:03Z","message":"Adding user profiles tests for regular and serverless (#171554)\n\n## Summary\r\n\r\nAdding functional tests for User Profiles and Dark Mode\r\n\r\n\r\n## Flaky Test Runner for new tests\r\n\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/4034\r\n🟢","sha":"66019dfe057734f4f45035e7df101822e1bcdcc5","branchLabelMapping":{"^v8.12.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:skip","backport:prev-minor","v8.12.0"],"number":171554,"url":"https://github.com/elastic/kibana/pull/171554","mergeCommit":{"message":"Adding user profiles tests for regular and serverless (#171554)\n\n## Summary\r\n\r\nAdding functional tests for User Profiles and Dark Mode\r\n\r\n\r\n## Flaky Test Runner for new tests\r\n\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/4034\r\n🟢","sha":"66019dfe057734f4f45035e7df101822e1bcdcc5"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v8.12.0","labelRegex":"^v8.12.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/171554","number":171554,"mergeCommit":{"message":"Adding user profiles tests for regular and serverless (#171554)\n\n## Summary\r\n\r\nAdding functional tests for User Profiles and Dark Mode\r\n\r\n\r\n## Flaky Test Runner for new tests\r\n\r\nhttps://buildkite.com/elastic/kibana-flaky-test-suite-runner/builds/4034\r\n🟢","sha":"66019dfe057734f4f45035e7df101822e1bcdcc5"}}]}] BACKPORT--> Co-authored-by: Kurt <kc13greiner@users.noreply.github.com>
This commit is contained in:
parent
3aadaa37e4
commit
416cc7f8c0
9 changed files with 343 additions and 3 deletions
|
@ -345,6 +345,7 @@ enabled:
|
|||
- x-pack/test/functional/apps/transform/feature_controls/config.ts
|
||||
- x-pack/test/functional/apps/upgrade_assistant/config.ts
|
||||
- x-pack/test/functional/apps/uptime/config.ts
|
||||
- x-pack/test/functional/apps/user_profiles/config.ts
|
||||
- x-pack/test/functional/apps/visualize/config.ts
|
||||
- x-pack/test/functional/apps/watcher/config.ts
|
||||
- x-pack/test/functional/config_security_basic.ts
|
||||
|
|
|
@ -138,7 +138,7 @@ const UserDetailsEditor: FunctionComponent<UserDetailsEditorProps> = ({ user })
|
|||
labelAppend={<OptionalText />}
|
||||
fullWidth
|
||||
>
|
||||
<FormField name="user.full_name" fullWidth />
|
||||
<FormField name="user.full_name" data-test-subj={'userProfileFullName'} fullWidth />
|
||||
</FormRow>
|
||||
|
||||
<FormRow
|
||||
|
@ -153,7 +153,7 @@ const UserDetailsEditor: FunctionComponent<UserDetailsEditorProps> = ({ user })
|
|||
labelAppend={<OptionalText />}
|
||||
fullWidth
|
||||
>
|
||||
<FormField type="email" name="user.email" fullWidth />
|
||||
<FormField type="email" name="user.email" data-test-subj={'userProfileEmail'} fullWidth />
|
||||
</FormRow>
|
||||
</EuiDescribedFormGroup>
|
||||
);
|
||||
|
@ -189,6 +189,7 @@ const UserSettingsEditor: FunctionComponent<UserSettingsEditorProps> = ({
|
|||
<EuiKeyPadMenuItem
|
||||
name={id}
|
||||
label={label}
|
||||
data-test-subj={`themeKeyPadItem${label}`}
|
||||
checkable="single"
|
||||
isSelected={idSelected === id}
|
||||
isDisabled={isThemeOverridden}
|
||||
|
@ -810,7 +811,11 @@ export const UserProfile: FunctionComponent<UserProfileProps> = ({ user, data })
|
|||
</Form>
|
||||
</KibanaPageTemplate.Section>
|
||||
{formChanges.count > 0 ? (
|
||||
<KibanaPageTemplate.BottomBar paddingSize="m" position="fixed">
|
||||
<KibanaPageTemplate.BottomBar
|
||||
paddingSize="m"
|
||||
position="fixed"
|
||||
data-test-subj={'userProfileBottomBar'}
|
||||
>
|
||||
<SaveChangesBottomBar />
|
||||
</KibanaPageTemplate.BottomBar>
|
||||
) : null}
|
||||
|
@ -974,6 +979,7 @@ export const SaveChangesBottomBar: FunctionComponent = () => {
|
|||
<EuiFlexItem grow={false}>
|
||||
<EuiButton
|
||||
onClick={formik.submitForm}
|
||||
data-test-subj="saveProfileChangesButton"
|
||||
isLoading={formik.isSubmitting}
|
||||
isDisabled={formik.submitCount > 0 && !formik.isValid}
|
||||
color="success"
|
||||
|
|
17
x-pack/test/functional/apps/user_profiles/config.ts
Normal file
17
x-pack/test/functional/apps/user_profiles/config.ts
Normal file
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import { FtrConfigProviderContext } from '@kbn/test';
|
||||
|
||||
export default async function ({ readConfigFile }: FtrConfigProviderContext) {
|
||||
const functionalConfig = await readConfigFile(require.resolve('../../config.base.js'));
|
||||
|
||||
return {
|
||||
...functionalConfig.getAll(),
|
||||
testFiles: [require.resolve('.')],
|
||||
};
|
||||
}
|
14
x-pack/test/functional/apps/user_profiles/index.ts
Normal file
14
x-pack/test/functional/apps/user_profiles/index.ts
Normal file
|
@ -0,0 +1,14 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import { FtrProviderContext } from '../../ftr_provider_context';
|
||||
|
||||
export default ({ loadTestFile }: FtrProviderContext) => {
|
||||
describe('User Profiles page', function () {
|
||||
loadTestFile(require.resolve('./user_profiles'));
|
||||
});
|
||||
};
|
160
x-pack/test/functional/apps/user_profiles/user_profiles.ts
Normal file
160
x-pack/test/functional/apps/user_profiles/user_profiles.ts
Normal file
|
@ -0,0 +1,160 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import expect from '@kbn/expect';
|
||||
import { FtrProviderContext } from '../../ftr_provider_context';
|
||||
|
||||
export default ({ getPageObjects }: FtrProviderContext) => {
|
||||
const pageObjects = getPageObjects(['common', 'userProfiles', 'settings']);
|
||||
|
||||
describe('User Profile Page', async () => {
|
||||
before(async () => {});
|
||||
|
||||
describe('Details', async () => {
|
||||
before(async () => {
|
||||
await pageObjects.common.navigateToApp('security_account');
|
||||
});
|
||||
|
||||
it('should set the full name', async () => {
|
||||
await pageObjects.userProfiles.setFullNameInputField('Test User 2');
|
||||
|
||||
await pageObjects.userProfiles.saveUserProfileChanges();
|
||||
|
||||
let toast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(toast).to.be('Profile updated');
|
||||
|
||||
await pageObjects.userProfiles.setFullNameInputField('test user');
|
||||
|
||||
await pageObjects.userProfiles.saveUserProfileChanges();
|
||||
|
||||
toast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(toast).to.be('Profile updated');
|
||||
});
|
||||
|
||||
it('should set the email', async () => {
|
||||
await pageObjects.userProfiles.setEmailInputField('test@test.com');
|
||||
|
||||
await pageObjects.userProfiles.saveUserProfileChanges();
|
||||
|
||||
let toast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(toast).to.be('Profile updated');
|
||||
|
||||
await pageObjects.userProfiles.setEmailInputField('', true);
|
||||
|
||||
await pageObjects.userProfiles.saveUserProfileChanges();
|
||||
|
||||
toast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(toast).to.be('Profile updated');
|
||||
});
|
||||
});
|
||||
|
||||
describe('Change Password', async () => {
|
||||
before(async () => {
|
||||
await pageObjects.common.navigateToApp('security_account');
|
||||
});
|
||||
|
||||
it('should set the current password and enter a new password, then submit', async () => {
|
||||
const changePasswordButton = await pageObjects.userProfiles.getChangePasswordButton();
|
||||
await changePasswordButton.click();
|
||||
|
||||
await pageObjects.userProfiles.setCurrentPasswordField('changeme');
|
||||
await pageObjects.userProfiles.setNewPasswordField('changeme2');
|
||||
await pageObjects.userProfiles.setConfirmPasswordField('changeme2');
|
||||
|
||||
const submitButton = await pageObjects.userProfiles.getChangePasswordFormSubmitButton();
|
||||
await submitButton.click();
|
||||
|
||||
const initialToast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(initialToast).to.be('Password successfully changed');
|
||||
|
||||
await changePasswordButton.click();
|
||||
|
||||
await pageObjects.userProfiles.setCurrentPasswordField('changeme2');
|
||||
await pageObjects.userProfiles.setNewPasswordField('changeme');
|
||||
await pageObjects.userProfiles.setConfirmPasswordField('changeme');
|
||||
|
||||
await submitButton.click();
|
||||
|
||||
const resetToast = await pageObjects.common.closeToast();
|
||||
|
||||
expect(resetToast).to.be('Password successfully changed');
|
||||
});
|
||||
});
|
||||
|
||||
describe('Theme', async () => {
|
||||
it('should change theme based on the User Profile Theme control with default Adv. Settings value (light)', async () => {
|
||||
await pageObjects.common.navigateToApp('security_account');
|
||||
|
||||
const themeKeyPadMenu = await pageObjects.userProfiles.getThemeKeypadMenu();
|
||||
expect(themeKeyPadMenu).not.to.be(null);
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Dark');
|
||||
const darkModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(darkModeTag).to.be('v8dark');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Light');
|
||||
const lightModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(lightModeTag).to.be('v8light');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Space default');
|
||||
const spaceDefaultModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(spaceDefaultModeTag).to.be('v8light');
|
||||
});
|
||||
|
||||
it('should change theme based on the User Profile Theme control with default Adv. Settings value set to dark', async () => {
|
||||
await pageObjects.common.navigateToUrl('management', 'kibana/settings', {
|
||||
basePath: '',
|
||||
ensureCurrentUrl: false,
|
||||
shouldLoginIfPrompted: false,
|
||||
shouldUseHashForSubUrl: false,
|
||||
});
|
||||
|
||||
let advancedSetting = await pageObjects.settings.getAdvancedSettingCheckbox(
|
||||
'theme:darkMode'
|
||||
);
|
||||
expect(advancedSetting).to.be(null);
|
||||
|
||||
await pageObjects.settings.toggleAdvancedSettingCheckbox('theme:darkMode', true);
|
||||
advancedSetting = await pageObjects.settings.getAdvancedSettingCheckbox('theme:darkMode');
|
||||
expect(advancedSetting).to.be('true');
|
||||
|
||||
await pageObjects.common.navigateToApp('security_account');
|
||||
|
||||
let spaceDefaultModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(spaceDefaultModeTag).to.be('v8dark');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Light');
|
||||
const lightModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(lightModeTag).to.be('v8light');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Dark');
|
||||
const darkModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(darkModeTag).to.be('v8dark');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Space default');
|
||||
spaceDefaultModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(spaceDefaultModeTag).to.be('v8dark');
|
||||
|
||||
await pageObjects.common.navigateToUrl('management', 'kibana/settings', {
|
||||
basePath: '',
|
||||
ensureCurrentUrl: false,
|
||||
shouldLoginIfPrompted: false,
|
||||
shouldUseHashForSubUrl: false,
|
||||
});
|
||||
|
||||
await pageObjects.settings.toggleAdvancedSettingCheckbox('theme:darkMode', false);
|
||||
advancedSetting = await pageObjects.settings.getAdvancedSettingCheckbox('theme:darkMode');
|
||||
expect(advancedSetting).to.be(null);
|
||||
});
|
||||
});
|
||||
});
|
||||
};
|
|
@ -48,6 +48,7 @@ import { StatusPageObject } from './status_page';
|
|||
import { TagManagementPageObject } from './tag_management_page';
|
||||
import { UpgradeAssistantPageObject } from './upgrade_assistant_page';
|
||||
import { UptimePageObject } from './uptime_page';
|
||||
import { UserProfilePageProvider } from './user_profile_page';
|
||||
import { WatcherPageObject } from './watcher_page';
|
||||
|
||||
// just like services, PageObjects are defined as a map of
|
||||
|
@ -95,5 +96,6 @@ export const pageObjects = {
|
|||
tagManagement: TagManagementPageObject,
|
||||
upgradeAssistant: UpgradeAssistantPageObject,
|
||||
uptime: UptimePageObject,
|
||||
userProfiles: UserProfilePageProvider,
|
||||
watcher: WatcherPageObject,
|
||||
};
|
||||
|
|
99
x-pack/test/functional/page_objects/user_profile_page.ts
Normal file
99
x-pack/test/functional/page_objects/user_profile_page.ts
Normal file
|
@ -0,0 +1,99 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import expect from '@kbn/expect';
|
||||
import { FtrProviderContext } from '../ftr_provider_context';
|
||||
|
||||
export function UserProfilePageProvider({ getService }: FtrProviderContext) {
|
||||
const testSubjects = getService('testSubjects');
|
||||
const find = getService('find');
|
||||
const browser = getService('browser');
|
||||
const retry = getService('retry');
|
||||
|
||||
const getThemeTag = async (): Promise<void> => {
|
||||
return await browser.execute('return __kbnThemeTag__');
|
||||
};
|
||||
|
||||
const getSaveProfileChangesButton = async () => {
|
||||
return await testSubjects.find('saveProfileChangesButton');
|
||||
};
|
||||
|
||||
const getReloadWindowButton = async () => {
|
||||
return await testSubjects.find('windowReloadButton');
|
||||
};
|
||||
|
||||
const getThemeKeypadButton = async (option: string) => {
|
||||
option = option[0].toUpperCase() + option.substring(1).toLowerCase();
|
||||
return await testSubjects.find(`themeKeyPadItem${option}`);
|
||||
};
|
||||
|
||||
const saveUserProfileChanges = async (): Promise<void> => {
|
||||
let saveProfileChangesButton;
|
||||
await retry.try(async () => {
|
||||
saveProfileChangesButton = await getSaveProfileChangesButton();
|
||||
expect(saveProfileChangesButton).not.to.be(null);
|
||||
await saveProfileChangesButton.click();
|
||||
});
|
||||
};
|
||||
|
||||
const changeUserProfileTheme = async (theme: string): Promise<void> => {
|
||||
const themeModeButton = await getThemeKeypadButton(theme);
|
||||
expect(themeModeButton).not.to.be(null);
|
||||
await themeModeButton.click();
|
||||
|
||||
await saveUserProfileChanges();
|
||||
|
||||
let reloadWindowButton;
|
||||
await retry.try(async () => {
|
||||
reloadWindowButton = await getReloadWindowButton();
|
||||
expect(reloadWindowButton).not.to.be(null);
|
||||
await reloadWindowButton.click();
|
||||
});
|
||||
};
|
||||
|
||||
return {
|
||||
async getThemeKeypadMenu() {
|
||||
return await find.byCssSelector('.euiKeyPadMenu');
|
||||
},
|
||||
|
||||
async setFullNameInputField(newFullName: string) {
|
||||
return await testSubjects.setValue('userProfileFullName', newFullName);
|
||||
},
|
||||
|
||||
async setEmailInputField(newEmailAddress: string, clearWithKeyboard: boolean = false) {
|
||||
return await testSubjects.setValue('userProfileEmail', newEmailAddress, {
|
||||
clearWithKeyboard,
|
||||
});
|
||||
},
|
||||
|
||||
async getChangePasswordButton() {
|
||||
return await testSubjects.find('openChangePasswordForm');
|
||||
},
|
||||
|
||||
async setCurrentPasswordField(currentPassword: string) {
|
||||
return await testSubjects.setValue(
|
||||
'editUserChangePasswordCurrentPasswordInput',
|
||||
currentPassword
|
||||
);
|
||||
},
|
||||
|
||||
async setNewPasswordField(newPassword: string) {
|
||||
return await testSubjects.setValue('editUserChangePasswordNewPasswordInput', newPassword);
|
||||
},
|
||||
|
||||
async setConfirmPasswordField(newPassword: string) {
|
||||
return await testSubjects.setValue('editUserChangePasswordConfirmPasswordInput', newPassword);
|
||||
},
|
||||
|
||||
async getChangePasswordFormSubmitButton() {
|
||||
return await testSubjects.find('changePasswordFormSubmitButton');
|
||||
},
|
||||
getThemeTag,
|
||||
saveUserProfileChanges,
|
||||
changeUserProfileTheme,
|
||||
};
|
||||
}
|
|
@ -11,5 +11,6 @@ export default function ({ loadTestFile }: FtrProviderContext) {
|
|||
describe('Serverless Common UI - Platform Security', function () {
|
||||
loadTestFile(require.resolve('./api_keys'));
|
||||
loadTestFile(require.resolve('./navigation/avatar_menu'));
|
||||
loadTestFile(require.resolve('./user_profiles/user_profiles'));
|
||||
});
|
||||
}
|
||||
|
|
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import expect from '@kbn/expect';
|
||||
import { FtrProviderContext } from '../../../../ftr_provider_context';
|
||||
|
||||
export default function ({ getPageObjects }: FtrProviderContext) {
|
||||
const pageObjects = getPageObjects(['svlCommonPage', 'common', 'userProfiles']);
|
||||
|
||||
describe('User Profile Page', async () => {
|
||||
before(async () => {
|
||||
await pageObjects.svlCommonPage.login();
|
||||
});
|
||||
|
||||
describe('Theme', async () => {
|
||||
it('should change theme based on the User Profile Theme control', async () => {
|
||||
await pageObjects.common.navigateToApp('security_account');
|
||||
|
||||
const themeKeyPadMenu = await pageObjects.userProfiles.getThemeKeypadMenu();
|
||||
expect(themeKeyPadMenu).not.to.be(null);
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Dark');
|
||||
const darkModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(darkModeTag).to.be('v8dark');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Light');
|
||||
const lightModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(lightModeTag).to.be('v8light');
|
||||
|
||||
await pageObjects.userProfiles.changeUserProfileTheme('Space default');
|
||||
const spaceDefaultModeTag = await pageObjects.userProfiles.getThemeTag();
|
||||
expect(spaceDefaultModeTag).to.be('v8light');
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue