Welcome to borrow-ui!

Bootstrap your React Component Library with yarn 3, TypeScript, Rollup and Storybook
Or try the components with yarn add @borrow-ui/ui
Small reusable components
Short code easy to understand, or clearly divided into readable sub-components.
Documented and tested
Each component is fully tested with react-testing-library and documented.
Easy to extend
Adding or removing components is simple, just follow the tutorial and you are ready to go!
TypeScript and Rollup
The main library is written in Typescript and bundled with Rollup, with optimized peer dependencies.
Storybook
Storybook support out of the box, directly connected to the components library.
BEM SCSS
Styles are easy to read and override in more complex scenarios.

Get the code

Author your own React Component Library in minutes!
Download the repository from the GitHub page
# or directly from command line
curl -LJO https://github.com/borrow-ui/borrow-ui/archive/master.zip

Structure your project

The repository is a Monorepo made withyarn workspaces.
If you don't want to use a Monorepo, just copy the ui folder inside your project and add the dependencies.
In the monorepo you will find the following packages:
  • ui: the UI library with components and styles
  • documentation: Storybook project already setup and connected to the components
  • dashboard: a simple dashboard demonstration
  • website-next: a website based on Next.js (your next blog engine?)

Rename

With your own favourite code editor, rename all occurrences of borrow-ui to your preferred name.

?

Why manually renaming?
A dedicated script is on the roadmap, in the meantime just use your favourite tools!

Example - Link component

Each component comes with React file(s) and asass file.
  • Components are exported inui/src/index.ts
  • Styles are included inui/src/style/ui.full.scss
The name of the UI library is saved into two configuration files and used across the files: by default it is set asborrow-ui.
BEM style is used to organize the styles and can be easily overridden.
Components accept many properties (for examplesize for icons) and always combine generated classes with the standard className.

ui/src/components/link/Link.tsx


import React from 'react';

import { UI_PREFIX, getConfig } from '../../config';
import { LinkProps } from './Link.types';

const LINK_CLASS = `${UI_PREFIX}__link`;

export const Link = ({
    className = '',
    children,
    ...rest
}: LinkProps): JSX.Element => {
    const linkClassName = `${LINK_CLASS} ${className}`.trim();

    return (
        <a className={linkClassName} {...rest}>
            {children}
        </a>
    );
};

ui/src/components/link/Link.types.ts


export interface LinkProps extends React.ComponentPropsWithoutRef<React.ElementType> {
    children: React.ReactNode;
    className?: string;
}

ui/src/components/link/link.test.js


import React from 'react';
import { render, screen } from '@testing-library/react';
import { UI_PREFIX } from '../../config';
import { Link } from './Link';

describe('Link', () => {
    test('renders the link with proper class', () => {
        render(<Link href="/app">App</Link>);

        const link = screen.getByText('App');
        expect(link).toHaveClass(UI_PREFIX + '__link');
    });
});

ui/src/components/link/link.scss


@import '../../vars/main';

.#{$ui-prefix}__link {
    color: $ui-color-accent;
    text-decoration: underline;
}
.#{$ui-prefix}__link:hover {
    color: $ui-color-accent-over;
}

ui/src/components/link/Link.stories.mdx


import { Meta, Story, Canvas, ArgsTable } from '@storybook/addon-docs';
import { Link } from './Link';

<Meta title="Components/Link" component={Link} />

# Link
Links are used to create connections.

<Canvas>
    <Story name="Default">
        <div>
            A normal link with "a" tag <Link>looks like this</Link>.
        </div>
    </Story>
</Canvas>

## Props
<ArgsTable of={Link} />
Each component comes with React file(s) and asass file.
  • Components are exported inui/src/index.js
  • Styles are included inui/src/style/ui.full.scss
The name of the UI library is saved into two configuration files and used across the files: by default it is set asborrow-ui.
BEM style is used to organize the styles and can be easily overridden.
Components accept many properties (for examplesize for icons) and always combine generated classes with the standard className.

ui/src/components/link/Link.js


import React from 'react';
import PropTypes from 'prop-types';

import { UI_PREFIX } from '../../config';
import { propTypesChildren } from '../../utils/types';

const LINK_CLASS = `${UI_PREFIX}__link`;

export function Link({ className = '', children, ...rest }) {
    const linkClassName = `${LINK_CLASS} ${className}`;

    return (
        <a className={linkClassName} {...rest}>
            {children}
        </a>
    );
}

Link.propTypes = {
    className: PropTypes.string,
    children: propTypesChildren,
};

ui/src/components/link/link.test.js


import React from 'react';
import { render, screen } from '@testing-library/react';
import { UI_PREFIX } from '../../config';
import { Link } from './Link';

describe('Link', () => {
    test('renders the link with proper class', () => {
        render(<Link href="/app">App</Link>);

        const link = screen.getByText('App');
        expect(link).toHaveClass(UI_PREFIX + '__link');
    });
});

ui/src/components/link/link.scss


@import '../../vars/main';

.#{$ui-prefix}__link {
    color: $ui-color-accent;
    text-decoration: underline;
}
.#{$ui-prefix}__link:hover {
    color: $ui-color-accent-over;
}

ui/src/components/link/Link.stories.mdx


import { Meta, Story, Canvas, ArgsTable } from '@storybook/addon-docs';
import { Link } from './Link';

<Meta title="Components/Link" component={Link} />

# Link
Links are used to create connections.

<Canvas>
    <Story name="Default">
        <div>
            A normal link with "a" tag <Link>looks like this</Link>.
        </div>
    </Story>
</Canvas>

## Props
<ArgsTable of={Link} />

Dashboard Example

Dashboard home screenshot
A dashboard demostration is available at https://dashboard.borrow-ui.dev.
You can find the code in the github repository. All the components are commented.
The dashboard is based on CRA and uses the latest stable version of borrow-ui.
As a small demo, it shows how to structure a dashboard with multiple applications and shared components, load entities (such as books and reviews) and how to use borrow-ui to create pages and forms.
The code of the dashboard is available in the packages/dashboard folder.

Website Example made with Next.js

Website Next home screenshot
A Next.js website is available at https://next.borrow-ui.dev.
Like the dashboard, you can find the code in the github repository under packages/website-next. The home page describes the features and the blog posts how the website works.
The website is based on Next.js and uses the latest stable version of borrow-ui.