Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Create Footer Component #5983

Merged
merged 1 commit into from
Oct 15, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 49 additions & 0 deletions components/sections/Footer/index.module.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
.footer {
@apply flex
flex-col
items-center
gap-6
px-8
py-4
md:flex-row
md:justify-between
md:py-5;

.sectionPrimary {
@apply flex
flex-wrap
content-start
items-center
justify-center
gap-1
self-stretch;

a {
@apply whitespace-nowrap;
}
}

.sectionSecondary {
@apply flex
flex-col
items-center
gap-1
md:flex-row;

.social {
@apply flex
items-center
gap-1;
}
}

.darkImage {
@apply hidden
dark:block;
}

.lightImage {
@apply block
dark:hidden;
}
}
10 changes: 10 additions & 0 deletions components/sections/Footer/index.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import type { Meta as MetaObj, StoryObj } from '@storybook/react';

import Footer from './index';

type Story = StoryObj<typeof Footer>;
type Meta = MetaObj<typeof Footer>;

export const Default: Story = {};

export default { component: Footer } as Meta;
58 changes: 58 additions & 0 deletions components/sections/Footer/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
import classNames from 'classnames';
import Image from 'next/image';
import type { FC } from 'react';
import { FormattedMessage } from 'react-intl';

import NavItem from '@/components/sections/NavItem';
import { useSiteConfig } from '@/hooks/useSiteConfig';

import styles from './index.module.css';

const Footer: FC = () => {
const { footerLinks, socialLinks } = useSiteConfig();

const openJSlink = footerLinks.at(-1)!;
ovflowd marked this conversation as resolved.
Show resolved Hide resolved

return (
<footer className={styles.footer}>
<div className={styles.sectionPrimary}>
{footerLinks.slice(0, -1).map(item => (
<NavItem type="footer" href={item.link} key={item.link}>
<FormattedMessage id={item.text} />
</NavItem>
))}
</div>
<div className={styles.sectionSecondary}>
<NavItem type="footer" href={openJSlink.link}>
&copy; <FormattedMessage id={openJSlink.text} />
</NavItem>
<div className={styles.social}>
{socialLinks.map(link => {
const navClass = classNames({
[styles.darkImage]: link.kind === 'dark',
[styles.lightImage]: link.kind === 'light',
ovflowd marked this conversation as resolved.
Show resolved Hide resolved
});

return (
<NavItem
className={navClass}
key={link.icon}
href={link.link}
type="footer"
ovflowd marked this conversation as resolved.
Show resolved Hide resolved
>
<Image
src={link.icon}
alt={link.alt || 'social'}
width={20}
height={20}
/>
</NavItem>
);
})}
</div>
</div>
</footer>
);
};

export default Footer;
13 changes: 10 additions & 3 deletions components/sections/NavItem/index.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,21 +8,28 @@ type Meta = MetaObj<typeof NavItem>;
export const Default: Story = {
args: {
href: '/learn',
label: 'Learn',
children: 'Learn',
},
};

export const WithExternalLink: Story = {
args: {
href: 'https://nodejs.org/en',
label: 'Learn',
children: 'Learn',
},
};

export const WithChildren: Story = {
args: {
href: 'https://nodejs.org/en',
children: <b>Learn</b>,
},
};

export const FooterItem: Story = {
args: {
href: '/about',
label: 'Trademark Policy',
children: 'Trademark Policy',
type: 'footer',
},
};
Expand Down
15 changes: 10 additions & 5 deletions components/sections/NavItem/index.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { ArrowUpRightIcon } from '@heroicons/react/24/solid';
import classNames from 'classnames';
import type { FC } from 'react';
import type { FC, PropsWithChildren } from 'react';
import { useMemo } from 'react';

import LocalizedLink from '@/components/LocalizedLink';
Expand All @@ -11,11 +11,16 @@ type NavItemType = 'nav' | 'footer';

type NavItemProps = {
href: string;
label?: string;
type?: NavItemType;
className?: string;
};

const NavItem: FC<NavItemProps> = ({ href, label, type = 'nav' }) => {
const NavItem: FC<PropsWithChildren<NavItemProps>> = ({
href,
type = 'nav',
children,
className,
}) => {
const showIcon = useMemo(
() => type === 'nav' && /^https?:\/\//.test(href),
[href, type]
Expand All @@ -24,9 +29,9 @@ const NavItem: FC<NavItemProps> = ({ href, label, type = 'nav' }) => {
return (
<LocalizedLink
href={href}
className={classNames(styles.navItem, styles[type])}
className={classNames(styles.navItem, styles[type], className)}
>
<span className={styles.label}>{label}</span>
<span className={styles.label}>{children}</span>
{showIcon && <ArrowUpRightIcon className={styles.icon} />}
</LocalizedLink>
);
Expand Down
5 changes: 5 additions & 0 deletions i18n/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,11 @@
"components.header.links.security": "Security",
"components.header.links.certification": "Certification",
"components.header.links.blog": "News",
"components.footer.links.trademarkPolicy": "Trademark Policy",
"components.footer.links.privacyPolicy": "Privacy Policy",
"components.footer.links.codeOfConduct": "Code of Conduct",
"components.footer.links.security": "Security",
"components.footer.links.openJS": "OpenJS Foundation",
"components.navigation.about.links.governance": "Governance",
"components.navigation.docs.links.es6": "ES6 and beyond",
"components.navigation.docs.links.apiLts": "{fullLtsNodeVersion} API {spanLts}",
Expand Down
6 changes: 4 additions & 2 deletions providers/siteProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@ import type { FC, PropsWithChildren } from 'react';
import { siteConfig } from '@/next.json.mjs';
import type { SiteConfig } from '@/types';

export const SiteContext = createContext<SiteConfig>(siteConfig);
const config = siteConfig as SiteConfig;

export const SiteContext = createContext<SiteConfig>(config);

export const SiteProvider: FC<PropsWithChildren> = ({ children }) => (
<SiteContext.Provider value={siteConfig}>{children}</SiteContext.Provider>
<SiteContext.Provider value={config}>{children}</SiteContext.Provider>
);
62 changes: 61 additions & 1 deletion site.json
Original file line number Diff line number Diff line change
Expand Up @@ -38,5 +38,65 @@
"text": "Security releases now available",
"link": "https://nodejs.org/en/blog/vulnerability/october-2023-security-releases/"
}
}
},
"footerLinks": [
{
"link": "https://openjsf.org/wp-content/uploads/sites/84/2021/01/OpenJS-Foundation-Trademark-Policy-2021-01-12.docx.pdf",
"text": "components.footer.links.trademarkPolicy"
},
{
"link": "https://openjsf.org/wp-content/uploads/sites/84/2021/04/OpenJS-Foundation-Privacy-Policy-2019-11-15.pdf",
"text": "components.footer.links.privacyPolicy"
},
{
"link": "https://github.com/openjs-foundation/cross-project-council/blob/main/CODE_OF_CONDUCT.md",
"text": "components.footer.links.codeOfConduct"
},
{
"link": "https://github.com/nodejs/node/blob/HEAD/SECURITY.md#security",
"text": "components.footer.links.security"
},
{
"link": "https://openjsf.org/",
"text": "components.footer.links.openJS"
}
],
"socialLinks": [
{
"icon": "/static/images/logos/social-github.svg",
"link": "https://github.com/nodejs/node",
"kind": "dark",
"alt": "GitHub"
},
{
"icon": "/static/images/logos/social-github-dark.svg",
"link": "https://github.com/nodejs/node",
"kind": "light",
"alt": "GitHub"
},
{
"icon": "/static/images/logos/social-mastodon.svg",
"link": "https://social.lfx.dev/@nodejs",
"kind": "neutral",
"alt": "Mastodon"
},
{
"icon": "/static/images/logos/social-twitter.svg",
ovflowd marked this conversation as resolved.
Show resolved Hide resolved
"link": "https://twitter.com/nodejs",
"kind": "neutral",
"alt": "Twitter"
},
{
"icon": "/static/images/logos/social-slack.svg",
"link": "https://openjs-foundation.slack.com/join/shared_invite/zt-238w9sb83-Qk9NcsrEMomq94Y~3gW8EQ#/shared-invite/email",
"kind": "neutral",
"alt": "Slack"
},
{
"icon": "/static/images/logos/social-linkedin.svg",
"link": "https://www.linkedin.com/company/node-js",
"kind": "neutral",
"alt": "LinkedIn"
}
]
}
14 changes: 14 additions & 0 deletions types/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,18 @@ export interface OGConfig {
imgHeight: string;
}

export interface FooterConfig {
text: string;
link: string;
}

export interface SocialConfig {
icon: string;
link: string;
kind: 'dark' | 'light' | 'neutral';
alt?: string;
}

export interface SiteConfig {
title: string;
description: string;
Expand All @@ -23,4 +35,6 @@ export interface SiteConfig {
twitter: TwitterConfig;
rssFeeds: Array<RSSFeed>;
websiteBanners: Record<string, WebsiteBanner>;
footerLinks: Array<FooterConfig>;
socialLinks: Array<SocialConfig>;
}
Loading