mirror of
https://github.com/SomboChea/ui
synced 2024-11-24 06:54:27 +07:00
fix: refactor/116 RegistryInfoContent is converted to functional component (#229)
* refactor:116[PackageList] component is converted to functional * Refactor:#116 - Registry info content is converted to functional component * refactor/116 - fix lint error * refactor:116 - more lint errors * refactor/116 - lint error * refactor:116 - remove snapshot * refactor: address code review comments #116 * refactor: fix lint error * refactor: code review changes * refactor add missed file * refactor: lint error * refactor: lint * refactor: lint * refactor: fix lint error
This commit is contained in:
parent
803da1c532
commit
b74ca2285e
@ -1,4 +1,4 @@
|
|||||||
import React, { Fragment, ReactElement } from 'react';
|
import React, { Fragment, ReactNode } from 'react';
|
||||||
|
|
||||||
import Package from '../Package';
|
import Package from '../Package';
|
||||||
import Help from '../Help';
|
import Help from '../Help';
|
||||||
@ -12,22 +12,23 @@ interface Props {
|
|||||||
packages: PackageInterface[];
|
packages: PackageInterface[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export const PackageList: React.FC<Props> = props => {
|
export const PackageList: React.FC<Props> = ({ packages }) => {
|
||||||
const renderPackages: () => ReactElement<HTMLElement>[] = () => {
|
const renderPackages: () => ReactNode[] = () => {
|
||||||
return props.packages.map((pkg, i) => {
|
return packages.map(({ name, version, description, time, keywords, dist, homepage, bugs, author, license }, i) => {
|
||||||
const { name, version, description, time, keywords, dist, homepage, bugs, author } = pkg;
|
|
||||||
// TODO: move format license to API side.
|
// TODO: move format license to API side.
|
||||||
const license = formatLicense(pkg.license);
|
const _license = formatLicense(license);
|
||||||
return (
|
return (
|
||||||
<Fragment key={i}>
|
<Fragment key={i}>
|
||||||
{i !== 0 && <Divider />}
|
{i !== 0 && <Divider />}
|
||||||
<Package {...{ name, dist, version, author, description, license, time, keywords, homepage, bugs }} />
|
<Package
|
||||||
|
{...{ name, dist, version, author, description, license: _license, time, keywords, homepage, bugs }}
|
||||||
|
/>
|
||||||
</Fragment>
|
</Fragment>
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
const hasPackages: () => boolean = () => props.packages.length > 0;
|
const hasPackages: () => boolean = () => packages.length > 0;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={'package-list-items'}>
|
<div className={'package-list-items'}>
|
||||||
|
@ -1,23 +1,35 @@
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { mount } from 'enzyme';
|
import { render, cleanup, fireEvent } from '@testing-library/react';
|
||||||
|
|
||||||
import RegistryInfoContent from './RegistryInfoContent';
|
import RegistryInfoContent from './RegistryInfoContent';
|
||||||
|
|
||||||
describe('<RegistryInfoContent /> component', () => {
|
describe('<RegistryInfoContent /> component', () => {
|
||||||
test('should render the component in default state with npm tab', () => {
|
afterEach(() => {
|
||||||
const wrapper = mount(<RegistryInfoContent registryUrl="https://registry.verdaccio.org" scope="@" />);
|
cleanup();
|
||||||
expect(wrapper.html()).toMatchSnapshot();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
test('should render the component in default state with pnpm tab', () => {
|
test('should load the component with no data', () => {
|
||||||
const wrapper = mount(<RegistryInfoContent registryUrl="https://registry.verdaccio.org" scope="@" />);
|
const { getByTestId } = render(<RegistryInfoContent registryUrl={''} scope={''} />);
|
||||||
wrapper.setState({ tabPosition: 1 });
|
const unorderedListOfTodos = getByTestId('tabs-el');
|
||||||
expect(wrapper.html()).toMatchSnapshot();
|
expect(unorderedListOfTodos.children.length).toBe(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('should render the component in default state with yarn tab', () => {
|
test('should load the appropiate tab content when the tab is clicked', () => {
|
||||||
const wrapper = mount(<RegistryInfoContent registryUrl="https://registry.verdaccio.org" scope="@" />);
|
const props = { registryUrl: 'http://localhost:4872', scope: '@' };
|
||||||
wrapper.setState({ tabPosition: 2 });
|
const pnpmTabTextContent = `pnpm adduser --registry ${props.registryUrl}`;
|
||||||
expect(wrapper.html()).toMatchSnapshot();
|
|
||||||
|
// Render the component.
|
||||||
|
const { container, getByTestId } = render(
|
||||||
|
<RegistryInfoContent registryUrl={props.registryUrl} scope={props.scope} />
|
||||||
|
);
|
||||||
|
|
||||||
|
// Assert the text content for pnpm tab is not present intially
|
||||||
|
expect(container.textContent).not.toContain(pnpmTabTextContent);
|
||||||
|
|
||||||
|
const pnpmTab = getByTestId('pnpm-tab');
|
||||||
|
fireEvent.click(pnpmTab);
|
||||||
|
|
||||||
|
// Assert the text content is correct after clicking on the tab.
|
||||||
|
expect(container.textContent).toContain(pnpmTabTextContent);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import React, { Component } from 'react';
|
import React, { useState } from 'react';
|
||||||
import { css } from 'emotion';
|
import { css } from 'emotion';
|
||||||
|
|
||||||
import CopyToClipBoard from '../CopyToClipBoard';
|
import CopyToClipBoard from '../CopyToClipBoard';
|
||||||
@ -11,8 +11,62 @@ import Tab from '../../muiComponents/Tab';
|
|||||||
import { CommandContainer } from './styles';
|
import { CommandContainer } from './styles';
|
||||||
import { Props, State } from './types';
|
import { Props, State } from './types';
|
||||||
|
|
||||||
/* eslint react/prop-types:0 */
|
const RegistryInfoContent: React.FC<Props> = props => {
|
||||||
function TabContainer({ children }): JSX.Element {
|
const [tabPosition, setTabPosition] = useState<State['tabPosition']>(0);
|
||||||
|
const handleChange = (event: React.ChangeEvent<{}>, tabPosition: number): void => {
|
||||||
|
event.preventDefault();
|
||||||
|
setTabPosition(tabPosition);
|
||||||
|
};
|
||||||
|
|
||||||
|
const renderNpmTab = (scope: string, registryUrl: string): JSX.Element => {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.npm} set`, scope, registryUrl)} />
|
||||||
|
<CopyToClipBoard text={getCLISetRegistry(`${NODE_MANAGER.npm} adduser`, registryUrl)} />
|
||||||
|
<CopyToClipBoard text={getCLIChangePassword(NODE_MANAGER.npm, registryUrl)} />
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const renderPnpmTab = (scope: string, registryUrl: string): JSX.Element => {
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.pnpm} set`, scope, registryUrl)} />
|
||||||
|
<CopyToClipBoard text={getCLISetRegistry(`${NODE_MANAGER.pnpm} adduser`, registryUrl)} />
|
||||||
|
<CopyToClipBoard text={getCLIChangePassword(NODE_MANAGER.pnpm, registryUrl)} />
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const renderYarnTab = (scope: string, registryUrl: string): JSX.Element => {
|
||||||
|
return <CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.yarn} config set`, scope, registryUrl)} />;
|
||||||
|
};
|
||||||
|
|
||||||
|
const renderTabs = (): JSX.Element => {
|
||||||
|
const { scope, registryUrl } = props;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Tabs
|
||||||
|
data-testid={'tabs-el'}
|
||||||
|
indicatorColor="primary"
|
||||||
|
onChange={handleChange}
|
||||||
|
textColor="primary"
|
||||||
|
value={tabPosition}
|
||||||
|
variant="fullWidth">
|
||||||
|
<Tab data-testid={'npm-tab'} label={NODE_MANAGER.npm} />
|
||||||
|
<Tab data-testid={'pnpm-tab'} label={NODE_MANAGER.pnpm} />
|
||||||
|
<Tab data-testid={'yarn-tab'} label={NODE_MANAGER.yarn} />
|
||||||
|
</Tabs>
|
||||||
|
{tabPosition === 0 && <TabContainer>{renderNpmTab(scope, registryUrl)}</TabContainer>}
|
||||||
|
{tabPosition === 1 && <TabContainer>{renderPnpmTab(scope, registryUrl)}</TabContainer>}
|
||||||
|
{tabPosition === 2 && <TabContainer>{renderYarnTab(scope, registryUrl)}</TabContainer>}
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
/* eslint react/prop-types:0 */
|
||||||
|
const TabContainer = ({ children }): JSX.Element => {
|
||||||
return (
|
return (
|
||||||
<CommandContainer>
|
<CommandContainer>
|
||||||
<Typography
|
<Typography
|
||||||
@ -25,72 +79,9 @@ function TabContainer({ children }): JSX.Element {
|
|||||||
</Typography>
|
</Typography>
|
||||||
</CommandContainer>
|
</CommandContainer>
|
||||||
);
|
);
|
||||||
}
|
|
||||||
|
|
||||||
class RegistryInfoContent extends Component<Props, State> {
|
|
||||||
public state = {
|
|
||||||
tabPosition: 0,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
public render(): JSX.Element {
|
return <div>{renderTabs()}</div>;
|
||||||
return <div>{this.renderTabs()}</div>;
|
};
|
||||||
}
|
|
||||||
|
|
||||||
private handleChange = (event: React.ChangeEvent<{}>, tabPosition: number) => {
|
|
||||||
event.preventDefault();
|
|
||||||
this.setState({ tabPosition });
|
|
||||||
};
|
|
||||||
|
|
||||||
private renderTabs(): JSX.Element {
|
|
||||||
const { scope, registryUrl } = this.props;
|
|
||||||
const { tabPosition } = this.state;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<React.Fragment>
|
|
||||||
<Tabs
|
|
||||||
indicatorColor="primary"
|
|
||||||
onChange={this.handleChange}
|
|
||||||
textColor="primary"
|
|
||||||
value={tabPosition}
|
|
||||||
variant="fullWidth">
|
|
||||||
<Tab label={NODE_MANAGER.npm} />
|
|
||||||
<Tab label={NODE_MANAGER.pnpm} />
|
|
||||||
<Tab label={NODE_MANAGER.yarn} />
|
|
||||||
</Tabs>
|
|
||||||
{tabPosition === 0 && <TabContainer>{this.renderNpmTab(scope, registryUrl)}</TabContainer>}
|
|
||||||
{tabPosition === 1 && <TabContainer>{this.renderPNpmTab(scope, registryUrl)}</TabContainer>}
|
|
||||||
{tabPosition === 2 && <TabContainer>{this.renderYarnTab(scope, registryUrl)}</TabContainer>}
|
|
||||||
</React.Fragment>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
private renderNpmTab(scope: string, registryUrl: string): JSX.Element {
|
|
||||||
return (
|
|
||||||
<React.Fragment>
|
|
||||||
<CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.npm} set`, scope, registryUrl)} />
|
|
||||||
<CopyToClipBoard text={getCLISetRegistry(`${NODE_MANAGER.npm} adduser`, registryUrl)} />
|
|
||||||
<CopyToClipBoard text={getCLIChangePassword(NODE_MANAGER.npm, registryUrl)} />
|
|
||||||
</React.Fragment>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
private renderPNpmTab(scope: string, registryUrl: string): JSX.Element {
|
|
||||||
return (
|
|
||||||
<React.Fragment>
|
|
||||||
<CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.pnpm} set`, scope, registryUrl)} />
|
|
||||||
<CopyToClipBoard text={getCLISetRegistry(`${NODE_MANAGER.pnpm} adduser`, registryUrl)} />
|
|
||||||
<CopyToClipBoard text={getCLIChangePassword(NODE_MANAGER.pnpm, registryUrl)} />
|
|
||||||
</React.Fragment>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
private renderYarnTab(scope: string, registryUrl: string): JSX.Element {
|
|
||||||
return (
|
|
||||||
<React.Fragment>
|
|
||||||
<CopyToClipBoard text={getCLISetConfigRegistry(`${NODE_MANAGER.yarn} config set`, scope, registryUrl)} />
|
|
||||||
</React.Fragment>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export default RegistryInfoContent;
|
export default RegistryInfoContent;
|
||||||
|
@ -1,7 +0,0 @@
|
|||||||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
|
||||||
|
|
||||||
exports[`<RegistryInfoContent /> component should render the component in default state with npm tab 1`] = `"<div><div class=\\"MuiTabs-root\\"><div class=\\"MuiTabs-scroller MuiTabs-fixed\\" style=\\"overflow: hidden;\\"><div class=\\"MuiTabs-flexContainer\\" role=\\"tablist\\"><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary Mui-selected MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"true\\"><span class=\\"MuiTab-wrapper\\">npm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">pnpm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">yarn</span><span class=\\"MuiTouchRipple-root\\"></span></button></div><span class=\\"PrivateTabIndicator-root-25 PrivateTabIndicator-colorPrimary-26 MuiTabs-indicator\\" style=\\"left: 0px; width: 0px;\\"></span></div></div><div class=\\"css-1qvg11o ehfwshd0\\"><div class=\\"MuiTypography-root css-17iubtz MuiTypography-h6\\"><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">npm set @registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">npm adduser --registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">npm profile set password --registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div></div></div></div>"`;
|
|
||||||
|
|
||||||
exports[`<RegistryInfoContent /> component should render the component in default state with pnpm tab 1`] = `"<div><div class=\\"MuiTabs-root\\"><div class=\\"MuiTabs-scroller MuiTabs-fixed\\" style=\\"overflow: hidden;\\"><div class=\\"MuiTabs-flexContainer\\" role=\\"tablist\\"><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">npm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary Mui-selected MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"true\\"><span class=\\"MuiTab-wrapper\\">pnpm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">yarn</span><span class=\\"MuiTouchRipple-root\\"></span></button></div><span class=\\"PrivateTabIndicator-root-25 PrivateTabIndicator-colorPrimary-26 MuiTabs-indicator\\" style=\\"left: 0px; width: 0px;\\"></span></div></div><div class=\\"css-1qvg11o ehfwshd0\\"><div class=\\"MuiTypography-root css-17iubtz MuiTypography-h6\\"><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">pnpm set @registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">pnpm adduser --registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">pnpm profile set password --registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div></div></div></div>"`;
|
|
||||||
|
|
||||||
exports[`<RegistryInfoContent /> component should render the component in default state with yarn tab 1`] = `"<div><div class=\\"MuiTabs-root\\"><div class=\\"MuiTabs-scroller MuiTabs-fixed\\" style=\\"overflow: hidden;\\"><div class=\\"MuiTabs-flexContainer\\" role=\\"tablist\\"><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">npm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"false\\"><span class=\\"MuiTab-wrapper\\">pnpm</span><span class=\\"MuiTouchRipple-root\\"></span></button><button class=\\"MuiButtonBase-root MuiTab-root MuiTab-textColorPrimary Mui-selected MuiTab-fullWidth\\" tabindex=\\"0\\" type=\\"button\\" role=\\"tab\\" aria-selected=\\"true\\"><span class=\\"MuiTab-wrapper\\">yarn</span><span class=\\"MuiTouchRipple-root\\"></span></button></div><span class=\\"PrivateTabIndicator-root-25 PrivateTabIndicator-colorPrimary-26 MuiTabs-indicator\\" style=\\"left: 0px; width: 0px;\\"></span></div></div><div class=\\"css-1qvg11o ehfwshd0\\"><div class=\\"MuiTypography-root css-17iubtz MuiTypography-h6\\"><div class=\\"css-1mta3t8 eb8w2fo0\\"><span class=\\"css-lh0wgu eb8w2fo1\\">yarn config set @registry https://registry.verdaccio.org</span><button class=\\"MuiButtonBase-root MuiIconButton-root css-0 eb8w2fo2\\" tabindex=\\"0\\" type=\\"button\\" title=\\"Copy to Clipboard\\"><span class=\\"MuiIconButton-label\\"><svg class=\\"MuiSvgIcon-root\\" focusable=\\"false\\" viewBox=\\"0 0 24 24\\" aria-hidden=\\"true\\" role=\\"presentation\\"><path d=\\"M16 1H4c-1.1 0-2 .9-2 2v14h2V3h12V1zm-1 4l6 6v10c0 1.1-.9 2-2 2H7.99C6.89 23 6 22.1 6 21l.01-14c0-1.1.89-2 1.99-2h7zm-1 7h5.5L14 6.5V12z\\"></path></svg></span><span class=\\"MuiTouchRipple-root\\"></span></button></div></div></div></div>"`;
|
|
Loading…
Reference in New Issue
Block a user