Skip to content

Commit 96f45ee

Browse files
refactor(react): update HeaderNavigation to functional component (#9911)
* refactor(react): update HeaderNavigation to functional component * chore: remove ref from refactor Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
1 parent 51ccb35 commit 96f45ee

5 files changed

Lines changed: 129 additions & 5 deletions

File tree

docs/migration/11.x-carbon-components-react.md

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
## Table of Contents
99

1010
- [Components](#components)
11-
- [SideNavMenu](#sidenavmenu)
1211

1312
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
1413
<!-- prettier-ignore-end -->
@@ -32,8 +31,9 @@ For a full overview of changes to components, checkout our
3231

3332
## Components
3433

35-
| Component | Changes |
36-
| :------------ | :-------------------------------------------------------------- |
37-
| `SideNavMenu` | Updated from a class to functional component. No other changes. |
34+
| Component | Changes |
35+
| :----------------- | :-------------------------------------------------------------- |
36+
| `HeaderNavigation` | Updated from a class to functional component. No other changes. |
37+
| `SideNavMenu` | Updated from a class to functional component. No other changes. |
3838

3939
## FAQ

packages/react/src/components/UIShell/index.js

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@
66
*/
77

88
import * as FeatureFlags from '@carbon/feature-flags';
9+
import HeaderNavigationClassic from './HeaderNavigation';
10+
import { HeaderNavigation as HeaderNavigationNext } from './next';
911
import SideNavMenuClassic from './SideNavMenu';
1012
import { SideNavMenu as SideNavMenuNext } from './next/SideNavMenu';
1113

@@ -19,7 +21,9 @@ export HeaderMenu from './HeaderMenu';
1921
export HeaderMenuButton from './HeaderMenuButton';
2022
export HeaderMenuItem from './HeaderMenuItem';
2123
export HeaderName from './HeaderName';
22-
export HeaderNavigation from './HeaderNavigation';
24+
export const HeaderNavigation = FeatureFlags.enabled('enable-v11-release')
25+
? HeaderNavigationNext
26+
: HeaderNavigationClassic;
2327
export HeaderPanel from './HeaderPanel';
2428
export HeaderSideNavItems from './HeaderSideNavItems';
2529
export Switcher from './Switcher';
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
/**
2+
* Copyright IBM Corp. 2016, 2018
3+
*
4+
* This source code is licensed under the Apache-2.0 license found in the
5+
* LICENSE file in the root directory of this source tree.
6+
*/
7+
8+
import cx from 'classnames';
9+
import React from 'react';
10+
import PropTypes from 'prop-types';
11+
import { AriaLabelPropType } from '../../../prop-types/AriaPropTypes';
12+
import { usePrefix } from '../../../internal/usePrefix';
13+
14+
function HeaderNavigation(props) {
15+
const {
16+
'aria-label': ariaLabel,
17+
'aria-labelledby': ariaLabelledBy,
18+
children,
19+
className: customClassName,
20+
...rest
21+
} = props;
22+
const prefix = usePrefix();
23+
const className = cx(`${prefix}--header__nav`, customClassName);
24+
// Assign both label strategies in this option, only one should be defined
25+
// so when we spread that should be the one that is applied to the node
26+
const accessibilityLabel = {
27+
'aria-label': ariaLabel,
28+
'aria-labelledby': ariaLabelledBy,
29+
};
30+
31+
return (
32+
<nav {...rest} {...accessibilityLabel} className={className}>
33+
<ul className={`${prefix}--header__menu-bar`}>{children}</ul>
34+
</nav>
35+
);
36+
}
37+
38+
HeaderNavigation.propTypes = {
39+
/**
40+
* Required props for accessibility label on the underlying menu
41+
*/
42+
...AriaLabelPropType,
43+
44+
/**
45+
* Provide valid children of HeaderNavigation, for example `HeaderMenuItem`
46+
* or `HeaderMenu`
47+
*/
48+
children: PropTypes.node,
49+
50+
/**
51+
* Optionally provide a custom class to apply to the underlying <nav> node
52+
*/
53+
className: PropTypes.string,
54+
};
55+
56+
export { HeaderNavigation };
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
/**
2+
* Copyright IBM Corp. 2016, 2018
3+
*
4+
* This source code is licensed under the Apache-2.0 license found in the
5+
* LICENSE file in the root directory of this source tree.
6+
*/
7+
8+
import { cleanup, render, screen } from '@testing-library/react';
9+
import React from 'react';
10+
import { HeaderNavigation } from '../HeaderNavigation';
11+
12+
describe('HeaderNavigation', () => {
13+
it('should render children that are passed to the component', () => {
14+
render(
15+
<HeaderNavigation aria-label="navigation">
16+
<li data-testid="child" />
17+
</HeaderNavigation>
18+
);
19+
expect(screen.getByTestId('child')).toBeVisible();
20+
});
21+
22+
it('should add an accessibility label to the <nav>', () => {
23+
render(
24+
<HeaderNavigation aria-label="navigation">
25+
<li data-testid="child" />
26+
</HeaderNavigation>
27+
);
28+
29+
expect(screen.getByLabelText('navigation')).toBeVisible();
30+
31+
cleanup();
32+
render(
33+
<>
34+
<span id="label">navigation</span>
35+
<HeaderNavigation aria-labelledby="label">
36+
<li data-testid="child" />
37+
</HeaderNavigation>
38+
</>
39+
);
40+
41+
expect(screen.getByLabelText('navigation')).toBeVisible();
42+
});
43+
44+
it('should support a custom className', () => {
45+
const { container } = render(
46+
<HeaderNavigation aria-label="navigation" className="test">
47+
<li data-testid="child" />
48+
</HeaderNavigation>
49+
);
50+
51+
expect(container.firstChild).toHaveClass('test');
52+
});
53+
54+
it('should pass additional props to the outermost element', () => {
55+
const { container } = render(
56+
<HeaderNavigation aria-label="navigation" data-testid="test">
57+
<li data-testid="child" />
58+
</HeaderNavigation>
59+
);
60+
61+
expect(container.firstChild).toHaveAttribute('data-testid', 'test');
62+
});
63+
});

packages/react/src/components/UIShell/next/index.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,4 +5,5 @@
55
* LICENSE file in the root directory of this source tree.
66
*/
77

8+
export { HeaderNavigation } from './HeaderNavigation';
89
export { SideNavMenu } from './SideNavMenu';

0 commit comments

Comments
 (0)