+
+
+
diff --git a/src/plugins/home/public/application/components/welcome.test.tsx b/src/plugins/home/public/application/components/welcome.test.tsx
index 73d83dbdd2dc..8b48275656b9 100644
--- a/src/plugins/home/public/application/components/welcome.test.tsx
+++ b/src/plugins/home/public/application/components/welcome.test.tsx
@@ -51,67 +51,120 @@ test('should render a Welcome screen with the telemetry disclaimer', () => {
*/
const branding = {
+ darkMode: false,
mark: {
defaultUrl: '/',
},
applicationTitle: 'OpenSearch Dashboards',
};
-test('should render a Welcome screen with the telemetry disclaimer when optIn is true', () => {
- const telemetry = telemetryPluginMock.createStartContract();
- telemetry.telemetryService.getIsOptedIn = jest.fn().mockReturnValue(true);
- const component = shallow(
-
{}} telemetry={telemetry} branding={branding} />
- );
-
- expect(component).toMatchSnapshot();
-});
-
-test('should render a Welcome screen with the telemetry disclaimer when optIn is false', () => {
- const telemetry = telemetryPluginMock.createStartContract();
- telemetry.telemetryService.getIsOptedIn = jest.fn().mockReturnValue(false);
- const component = shallow(
- {}} telemetry={telemetry} branding={branding} />
- );
-
- expect(component).toMatchSnapshot();
-});
-
-test('should render a Welcome screen with no telemetry disclaimer', () => {
- const component = shallow( {}} branding={branding} />);
-
- expect(component).toMatchSnapshot();
-});
-
-test('fires opt-in seen when mounted', () => {
- const telemetry = telemetryPluginMock.createStartContract();
- const mockSetOptedInNoticeSeen = jest.fn();
- telemetry.telemetryNotifications.setOptedInNoticeSeen = mockSetOptedInNoticeSeen;
- shallow( {}} telemetry={telemetry} branding={branding} />);
-
- expect(mockSetOptedInNoticeSeen).toHaveBeenCalled();
-});
-
-test('should render a Welcome screen with the default OpenSearch Dashboards branding', () => {
- const defaultBranding = {
- mark: {},
- applicationTitle: 'OpenSearch Dashboards',
- };
- const component = shallow(
- {}} branding={defaultBranding} />
- );
- expect(component).toMatchSnapshot();
-});
-
-test('should render a Welcome screen with customized branding', () => {
- const customBranding = {
- mark: {
- defaultUrl: '/custom',
- },
- applicationTitle: 'custom title',
- };
- const component = shallow(
- {}} branding={customBranding} />
- );
- expect(component).toMatchSnapshot();
+describe('Welcome page ', () => {
+ describe('should render a Welcome screen ', () => {
+ test('with the telemetry disclaimer when optIn is true', () => {
+ const telemetry = telemetryPluginMock.createStartContract();
+ telemetry.telemetryService.getIsOptedIn = jest.fn().mockReturnValue(true);
+ const component = shallow(
+ {}} telemetry={telemetry} branding={branding} />
+ );
+
+ expect(component).toMatchSnapshot();
+ });
+
+ test('with the telemetry disclaimer when optIn is false', () => {
+ const telemetry = telemetryPluginMock.createStartContract();
+ telemetry.telemetryService.getIsOptedIn = jest.fn().mockReturnValue(false);
+ const component = shallow(
+ {}} telemetry={telemetry} branding={branding} />
+ );
+
+ expect(component).toMatchSnapshot();
+ });
+
+ test('with no telemetry disclaimer', () => {
+ const component = shallow( {}} branding={branding} />);
+
+ expect(component).toMatchSnapshot();
+ });
+
+ test('fires opt-in seen when mounted', () => {
+ const telemetry = telemetryPluginMock.createStartContract();
+ const mockSetOptedInNoticeSeen = jest.fn();
+ telemetry.telemetryNotifications.setOptedInNoticeSeen = mockSetOptedInNoticeSeen;
+ shallow(
+ {}} telemetry={telemetry} branding={branding} />
+ );
+
+ expect(mockSetOptedInNoticeSeen).toHaveBeenCalled();
+ });
+ });
+
+ describe('should render welcome logo in default mode ', () => {
+ test('using mark default mode URL', () => {
+ const customBranding = {
+ darkMode: false,
+ mark: {
+ defaultUrl: '/defaultModeMark',
+ },
+ applicationTitle: 'custom title',
+ };
+ const component = shallow(
+ {}} branding={customBranding} />
+ );
+ expect(component).toMatchSnapshot();
+ });
+
+ test('using the original OpenSearch Dashboards logo', () => {
+ const defaultBranding = {
+ darkMode: false,
+ mark: {},
+ applicationTitle: 'OpenSearch Dashboards',
+ };
+ const component = shallow(
+ {}} branding={defaultBranding} />
+ );
+ expect(component).toMatchSnapshot();
+ });
+ });
+ describe('should render welcome logo in dark mode ', () => {
+ test('using mark dark mode URL', () => {
+ const customBranding = {
+ darkMode: true,
+ mark: {
+ defaultUrl: '/defaultModeMark',
+ darkModeUrl: '/darkModeMark',
+ },
+ title: 'custom title',
+ };
+ const component = shallow(
+ {}} branding={customBranding} />
+ );
+ expect(component).toMatchSnapshot();
+ });
+
+ test('using mark default mode URL', () => {
+ const customBranding = {
+ darkMode: true,
+ mark: {
+ defaultUrl: '/defaultModeMark',
+ },
+ title: 'custom title',
+ };
+ const component = shallow(
+ {}} branding={customBranding} />
+ );
+ expect(component).toMatchSnapshot();
+ });
+
+ test('using the original opensearch logo', () => {
+ const customBranding = {
+ darkMode: true,
+ mark: {},
+ title: 'custom title',
+ };
+ const component = shallow(
+ {}} branding={customBranding} />
+ );
+ expect(component).toMatchSnapshot();
+ });
+ });
});
diff --git a/src/plugins/home/public/application/components/welcome.tsx b/src/plugins/home/public/application/components/welcome.tsx
index 2c5659a959c7..7574526f327f 100644
--- a/src/plugins/home/public/application/components/welcome.tsx
+++ b/src/plugins/home/public/application/components/welcome.tsx
@@ -59,6 +59,7 @@ interface Props {
onSkip: () => void;
telemetry?: TelemetryPluginStart;
branding: {
+ darkMode: boolean;
mark: {
defaultUrl?: string;
darkModeUrl?: string;
@@ -147,27 +148,74 @@ export class Welcome extends React.Component {
}
};
+ private darkMode = this.props.branding.darkMode;
+ private markDefault = this.props.branding.mark.defaultUrl;
+ private markDarkMode = this.props.branding.mark.darkModeUrl;
+ private applicationTitle = this.props.branding.applicationTitle;
+
+ /**
+ * Use branding configurations to check which URL to use for rendering
+ * welcome logo in default mode. In default mode, welcome logo will
+ * proritize default mode mark URL. If it is invalid, default opensearch logo
+ * will be rendered.
+ *
+ * @returns a valid custom URL or undefined if no valid URL is provided
+ */
+ private customWelcomeLogoDefaultMode = () => {
+ return this.markDefault ?? undefined;
+ };
+
+ /**
+ * Use branding configurations to check which URL to use for rendering
+ * welcome logo in dark mode. In dark mode, welcome logo will render
+ * dark mode mark URL if valid. Otherwise, it will render the default
+ * mode mark URL if valid. If both dark mode mark URL and default mode mark
+ * URL are invalid, the default opensearch logo will be rendered.
+ *
+ * @returns a valid custom URL or undefined if no valid URL is provided
+ */
+ private customWelcomeLogoDarkMode = () => {
+ return this.markDarkMode ?? this.markDefault ?? undefined;
+ };
+
+ /**
+ * Render custom welcome logo for both default mode and dark mode
+ *
+ * @returns a valid custom loading logo URL, or undefined
+ */
+ private customWelcomeLogo = () => {
+ if (this.darkMode) {
+ return this.customWelcomeLogoDarkMode();
+ }
+ return this.customWelcomeLogoDefaultMode();
+ };
+
+ /**
+ * Check if we render a custom welcome logo or the default opensearch spinner.
+ * If customWelcomeLogo() returns undefined(no valid custom URL is found), we
+ * render the default opensearch logo
+ *
+ * @returns a image component with custom logo URL, or the default opensearch logo
+ */
private renderBrandingEnabledOrDisabledLogo = () => {
- const mark = this.props.branding.mark.defaultUrl;
- if (!mark) {
- return (
-
-
-
- );
- } else {
+ if (this.customWelcomeLogo()) {
return (
);
}
+ return (
+
+
+
+ );
};
render() {
diff --git a/test/common/config.js b/test/common/config.js
index 2480cb416681..7ed1b32e50df 100644
--- a/test/common/config.js
+++ b/test/common/config.js
@@ -76,7 +76,9 @@ export default function () {
// `--newsfeed.service.pathTemplate=/api/_newsfeed-FTS-external-service-simulators/opensearch-dashboards/v{VERSION}.json`,
// Custom branding config
`--opensearchDashboards.branding.logo.defaultUrl=https://opensearch.org/assets/brand/SVG/Logo/opensearch_logo_default.svg`,
+ `--opensearchDashboards.branding.logo.darkModeUrl=https://opensearch.org/assets/brand/SVG/Logo/opensearch_logo_darkmode.svg`,
`--opensearchDashboards.branding.mark.defaultUrl=https://opensearch.org/assets/brand/SVG/Mark/opensearch_mark_default.svg`,
+ `--opensearchDashboards.branding.mark.darkModeUrl=https://opensearch.org/assets/brand/SVG/Mark/opensearch_mark_darkmode.svg`,
`--opensearchDashboards.branding.applicationTitle=OpenSearch`,
],
},
diff --git a/test/functional/apps/visualize/_custom_branding.js b/test/functional/apps/visualize/_custom_branding.js
index 54669990cf9f..0edf116d37b5 100644
--- a/test/functional/apps/visualize/_custom_branding.js
+++ b/test/functional/apps/visualize/_custom_branding.js
@@ -37,7 +37,7 @@ export default function ({ getService, getPageObjects }) {
const globalNav = getService('globalNav');
const opensearchArchiver = getService('opensearchArchiver');
const opensearchDashboardsServer = getService('opensearchDashboardsServer');
- const PageObjects = getPageObjects(['common', 'home', 'header']);
+ const PageObjects = getPageObjects(['common', 'home', 'header', 'settings']);
const testSubjects = getService('testSubjects');
describe('OpenSearch Dashboards branding configuration', function customHomeBranding() {
@@ -45,6 +45,8 @@ export default function ({ getService, getPageObjects }) {
this.tags('includeFirefox');
const expectedWelcomeLogo =
'https://opensearch.org/assets/brand/SVG/Mark/opensearch_mark_default.svg';
+ const expectedWelcomeLogoDarkmode =
+ 'https://opensearch.org/assets/brand/SVG/Mark/opensearch_mark_darkmode.svg';
const expectedWelcomeMessage = 'Welcome to OpenSearch';
//unloading any pre-existing settings so the welcome page will appear
@@ -84,19 +86,33 @@ export default function ({ getService, getPageObjects }) {
);
expect(actualLabel.toUpperCase()).to.equal(expectedWelcomeMessage.toUpperCase());
});
+
+ it('with customized logo in dark mode', async () => {
+ await PageObjects.common.navigateToApp('management/opensearch-dashboards/settings');
+ await PageObjects.settings.toggleAdvancedSettingCheckbox('theme:darkMode');
+ await PageObjects.common.navigateToApp('home');
+ await testSubjects.existOrFail('welcomeCustomLogo');
+ const actualLabel = await testSubjects.getAttribute(
+ 'welcomeCustomLogo',
+ 'data-test-image-url'
+ );
+ expect(actualLabel.toUpperCase()).to.equal(expectedWelcomeLogoDarkmode.toUpperCase());
+ });
});
describe('should render home page', async () => {
this.tags('includeFirefox');
- const expectedUrl =
+ const expectedHeaderLogo =
'https://opensearch.org/assets/brand/SVG/Logo/opensearch_logo_default.svg';
+ const expectedHeaderLogoDarkMode =
+ 'https://opensearch.org/assets/brand/SVG/Logo/opensearch_logo_darkmode.svg';
before(async function () {
await PageObjects.common.navigateToApp('home');
});
- it('with customized logo in Navbar', async () => {
- await globalNav.logoExistsOrFail(expectedUrl);
+ it('with customized logo in header bar', async () => {
+ await globalNav.logoExistsOrFail(expectedHeaderLogo);
});
it('with customized logo that can take back to home page', async () => {
@@ -106,6 +122,21 @@ export default function ({ getService, getPageObjects }) {
const url = await browser.getCurrentUrl();
expect(url.includes('/app/home')).to.be(true);
});
+
+ it('with customized logo in header bar in dark mode', async () => {
+ await PageObjects.common.navigateToApp('management/opensearch-dashboards/settings');
+ await PageObjects.settings.toggleAdvancedSettingCheckbox('theme:darkMode');
+ await PageObjects.common.navigateToApp('home');
+ await globalNav.logoExistsOrFail(expectedHeaderLogoDarkMode);
+ });
+
+ it('with customized logo that can take back to home page in dark mode', async () => {
+ await PageObjects.common.navigateToApp('settings');
+ await globalNav.clickLogo();
+ await PageObjects.header.waitUntilLoadingHasFinished();
+ const url = await browser.getCurrentUrl();
+ expect(url.includes('/app/home')).to.be(true);
+ });
});
});
}