From bdcec6de55168d37ca0c1e1783921ea2555e5c47 Mon Sep 17 00:00:00 2001 From: Juri Date: Mon, 24 Jul 2023 23:44:51 +0200 Subject: [PATCH] feat(nx-dev): github star widget --- .../feature-doc-viewer/src/lib/doc-viewer.tsx | 12 +++- .../src/lib/table-of-contents.tsx | 59 ++++++++++--------- nx-dev/nx-dev/lib/githubStars.api.ts | 33 +++++++++++ nx-dev/nx-dev/pages/[...segments].tsx | 27 ++++----- .../pages/extending-nx/[...segments].tsx | 7 +++ nx-dev/nx-dev/pages/extending-nx/index.tsx | 7 +++ .../nx-dev/pages/nx-cloud/[...segments].tsx | 7 +++ nx-dev/nx-dev/pages/nx-cloud/index.tsx | 7 +++ .../[name]/documents/[...segments].tsx | 7 +++ .../packages/rspack/documents/overview.tsx | 7 +++ .../rspack/documents/rspack-config-setup.tsx | 7 +++ .../rspack/documents/rspack-plugins.tsx | 7 +++ nx-dev/ui-common/src/index.ts | 1 + .../ui-common/src/lib/github-star-widget.tsx | 58 ++++++++++++++++++ 14 files changed, 203 insertions(+), 43 deletions(-) create mode 100644 nx-dev/nx-dev/lib/githubStars.api.ts create mode 100644 nx-dev/ui-common/src/lib/github-star-widget.tsx diff --git a/nx-dev/feature-doc-viewer/src/lib/doc-viewer.tsx b/nx-dev/feature-doc-viewer/src/lib/doc-viewer.tsx index 2188ffeded..b784f689bb 100644 --- a/nx-dev/feature-doc-viewer/src/lib/doc-viewer.tsx +++ b/nx-dev/feature-doc-viewer/src/lib/doc-viewer.tsx @@ -4,7 +4,7 @@ import { ProcessedDocument, RelatedDocument, } from '@nx/nx-dev/models-document'; -import { Breadcrumbs, Footer } from '@nx/nx-dev/ui-common'; +import { Breadcrumbs, Footer, GitHubStarWidget } from '@nx/nx-dev/ui-common'; import { renderMarkdown } from '@nx/nx-dev/ui-markdoc'; import { NextSeo } from 'next-seo'; import { useRouter } from 'next/router'; @@ -15,9 +15,11 @@ import { collectHeadings, TableOfContents } from './table-of-contents'; export function DocViewer({ document, relatedDocuments, + widgetData, }: { document: ProcessedDocument; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const hideTableOfContent = @@ -109,7 +111,13 @@ export function DocViewer({ elementRef={ref} path={router.basePath} headings={vm.tableOfContent} - /> + > + {widgetData.githubStarsCount > 0 && ( + + )} + )} diff --git a/nx-dev/feature-doc-viewer/src/lib/table-of-contents.tsx b/nx-dev/feature-doc-viewer/src/lib/table-of-contents.tsx index d7afc3a502..24bdabeb90 100644 --- a/nx-dev/feature-doc-viewer/src/lib/table-of-contents.tsx +++ b/nx-dev/feature-doc-viewer/src/lib/table-of-contents.tsx @@ -39,10 +39,12 @@ export function TableOfContents({ elementRef, headings, path, + children, }: { elementRef: any; headings: Heading[]; path: string; + children: React.ReactNode; }): JSX.Element { const headingLevelTargets: number[] = [1, 2, 3]; // matching to: H1, H2, H3... const items = headings.filter( @@ -60,32 +62,35 @@ export function TableOfContents({ ); return ( - + <> + +
{children}
+ ); } diff --git a/nx-dev/nx-dev/lib/githubStars.api.ts b/nx-dev/nx-dev/lib/githubStars.api.ts new file mode 100644 index 0000000000..329709ad51 --- /dev/null +++ b/nx-dev/nx-dev/lib/githubStars.api.ts @@ -0,0 +1,33 @@ +import { Octokit } from 'octokit'; + +let cachedGithubStarCountPromise: null | Promise = null; + +export async function fetchGithubStarCount() { + if (cachedGithubStarCountPromise !== null) { + // If the promise is in the cache, return it directly + return cachedGithubStarCountPromise; + } + + cachedGithubStarCountPromise = (async () => { + try { + const octokit = new Octokit({ auth: process.env.GITHUB_TOKEN }); + const responseData = await octokit.request('GET /repos/{owner}/{repo}', { + owner: 'nrwl', + repo: 'nx', + headers: { + 'X-GitHub-Api-Version': '2022-11-28', + }, + retry: { enabled: false }, + throttle: { + enabled: true, + }, + }); + + return responseData.data.stargazers_count; + } catch (e) { + return 0; // fallback, will hide GitHub star widget + } + })(); + + return cachedGithubStarCountPromise; +} diff --git a/nx-dev/nx-dev/pages/[...segments].tsx b/nx-dev/nx-dev/pages/[...segments].tsx index 249ddce33c..236a10d22e 100644 --- a/nx-dev/nx-dev/pages/[...segments].tsx +++ b/nx-dev/nx-dev/pages/[...segments].tsx @@ -1,7 +1,7 @@ import { getBasicNxSection } from '@nx/nx-dev/data-access-menu'; import { DocViewer } from '@nx/nx-dev/feature-doc-viewer'; import { ProcessedDocument, RelatedDocument } from '@nx/nx-dev/models-document'; -import { Menu, MenuItem } from '@nx/nx-dev/models-menu'; +import { MenuItem } from '@nx/nx-dev/models-menu'; import { DocumentationHeader, SidebarContainer } from '@nx/nx-dev/ui-common'; import { GetStaticPaths, GetStaticProps } from 'next'; import { useRouter } from 'next/router'; @@ -10,15 +10,18 @@ import { menusApi } from '../lib/menus.api'; import { useNavToggle } from '../lib/navigation-toggle.effect'; import { nxDocumentationApi } from '../lib/nx.api'; import { tagsApi } from '../lib/tags.api'; +import { fetchGithubStarCount } from '../lib/githubStars.api'; export default function NxDocumentation({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }) { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -40,16 +43,8 @@ export default function NxDocumentation({ return () => router.events.off('routeChangeComplete', handleRouteChange); }, [router, wrapperElement]); - const vm: { - document: ProcessedDocument; - menu: Menu; - relatedDocuments: RelatedDocument[]; - } = { - document, - menu: { - sections: [getBasicNxSection(menu)], - }, - relatedDocuments, + const menuWithSections = { + sections: [getBasicNxSection(menu)], }; return ( @@ -62,7 +57,7 @@ export default function NxDocumentation({ role="main" className="flex h-full flex-1 overflow-y-hidden" > - +
@@ -100,6 +96,9 @@ export const getStaticProps: GetStaticProps = async ({ return { props: { document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: tagsApi .getAssociatedItemsFromTags(document.tags) .filter((item) => item.path !== '/' + params.segments.join('/')), // Remove currently displayed item diff --git a/nx-dev/nx-dev/pages/extending-nx/[...segments].tsx b/nx-dev/nx-dev/pages/extending-nx/[...segments].tsx index 3e9c375f69..6b7128517c 100644 --- a/nx-dev/nx-dev/pages/extending-nx/[...segments].tsx +++ b/nx-dev/nx-dev/pages/extending-nx/[...segments].tsx @@ -10,15 +10,18 @@ import { menusApi } from '../../lib/menus.api'; import { useNavToggle } from '../../lib/navigation-toggle.effect'; import { nxPluginsApi } from '../../lib/plugins.api'; import { tagsApi } from '../../lib/tags.api'; +import { fetchGithubStarCount } from '../../lib/githubStars.api'; export default function Pages({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -72,6 +75,7 @@ export default function Pages({ @@ -98,6 +102,9 @@ export const getStaticProps: GetStaticProps = async ({ return { props: { document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: tagsApi .getAssociatedItemsFromTags(document.tags) .filter((item) => item.path !== '/' + segments.join('/')), // Remove currently displayed item diff --git a/nx-dev/nx-dev/pages/extending-nx/index.tsx b/nx-dev/nx-dev/pages/extending-nx/index.tsx index 1ace8563b1..5d8f92214e 100644 --- a/nx-dev/nx-dev/pages/extending-nx/index.tsx +++ b/nx-dev/nx-dev/pages/extending-nx/index.tsx @@ -10,15 +10,18 @@ import { menusApi } from '../../lib/menus.api'; import { useNavToggle } from '../../lib/navigation-toggle.effect'; import { nxPluginsApi } from '../../lib/plugins.api'; import { tagsApi } from '../../lib/tags.api'; +import { fetchGithubStarCount } from '../../lib/githubStars.api'; export default function PluginsRoot({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }) { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -72,6 +75,7 @@ export default function PluginsRoot({ @@ -87,6 +91,9 @@ export const getStaticProps: GetStaticProps = async () => { return { props: { document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, menu: menusApi.getMenu('extending-nx', ''), relatedDocuments: document.tags .map((t) => tagsApi.getAssociatedItems(t)) diff --git a/nx-dev/nx-dev/pages/nx-cloud/[...segments].tsx b/nx-dev/nx-dev/pages/nx-cloud/[...segments].tsx index 1bf55d9b57..b4d9791d0a 100644 --- a/nx-dev/nx-dev/pages/nx-cloud/[...segments].tsx +++ b/nx-dev/nx-dev/pages/nx-cloud/[...segments].tsx @@ -13,15 +13,18 @@ import { nxCloudApi } from '../../lib/cloud.api'; import { menusApi } from '../../lib/menus.api'; import { useNavToggle } from '../../lib/navigation-toggle.effect'; import { tagsApi } from '../../lib/tags.api'; +import { fetchGithubStarCount } from '../../lib/githubStars.api'; export default function Pages({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }) { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -75,6 +78,7 @@ export default function Pages({ @@ -99,6 +103,9 @@ export const getStaticProps: GetStaticProps = async ({ return { props: { document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: tagsApi .getAssociatedItemsFromTags(document.tags) .filter((item) => item.path !== '/' + segments.join('/')), // Remove currently displayed item diff --git a/nx-dev/nx-dev/pages/nx-cloud/index.tsx b/nx-dev/nx-dev/pages/nx-cloud/index.tsx index 4ae72535b8..9742328df4 100644 --- a/nx-dev/nx-dev/pages/nx-cloud/index.tsx +++ b/nx-dev/nx-dev/pages/nx-cloud/index.tsx @@ -13,15 +13,18 @@ import { nxCloudApi } from '../../lib/cloud.api'; import { menusApi } from '../../lib/menus.api'; import { useNavToggle } from '../../lib/navigation-toggle.effect'; import { tagsApi } from '../../lib/tags.api'; +import { fetchGithubStarCount } from '../../lib/githubStars.api'; export default function CloudRoot({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }) { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -75,6 +78,7 @@ export default function CloudRoot({ @@ -90,6 +94,9 @@ export const getStaticProps: GetStaticProps = async () => { return { props: { document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, menu: menusApi.getMenu('cloud', ''), relatedDocuments: document.tags .map((t) => tagsApi.getAssociatedItems(t)) diff --git a/nx-dev/nx-dev/pages/packages/[name]/documents/[...segments].tsx b/nx-dev/nx-dev/pages/packages/[name]/documents/[...segments].tsx index 5cb45d0b85..de802de867 100644 --- a/nx-dev/nx-dev/pages/packages/[name]/documents/[...segments].tsx +++ b/nx-dev/nx-dev/pages/packages/[name]/documents/[...segments].tsx @@ -13,16 +13,19 @@ import { menusApi } from '../../../../lib/menus.api'; import { useNavToggle } from '../../../../lib/navigation-toggle.effect'; import { nxPackagesApi } from '../../../../lib/packages.api'; import { tagsApi } from '../../../../lib/tags.api'; +import { fetchGithubStarCount } from '../../../../lib/githubStars.api'; export default function PackageDocument({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; pkg: ProcessedPackageMetadata; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -79,6 +82,7 @@ export default function PackageDocument({ @@ -120,6 +124,9 @@ export async function getStaticProps({ props: { pkg: nxPackagesApi.getPackage([params.name]), document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: tagsApi .getAssociatedItemsFromTags(document.tags) .filter((item) => item.path !== '/' + segments.join('/')), // Remove currently displayed item diff --git a/nx-dev/nx-dev/pages/packages/rspack/documents/overview.tsx b/nx-dev/nx-dev/pages/packages/rspack/documents/overview.tsx index e4e5960e2b..badb401320 100644 --- a/nx-dev/nx-dev/pages/packages/rspack/documents/overview.tsx +++ b/nx-dev/nx-dev/pages/packages/rspack/documents/overview.tsx @@ -11,16 +11,19 @@ import { menusApi } from '../../../../lib/menus.api'; import { useNavToggle } from '../../../../lib/navigation-toggle.effect'; import { content } from '../../../../lib/rspack/content/overview'; import { pkg } from '../../../../lib/rspack/pkg'; +import { fetchGithubStarCount } from '../../../../lib/githubStars.api'; export default function Overview({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; pkg: ProcessedPackageMetadata; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -77,6 +80,7 @@ export default function Overview({ @@ -99,6 +103,9 @@ export async function getStaticProps() { props: { pkg, document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: [], menu: menusApi.getMenu('packages', ''), }, diff --git a/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-config-setup.tsx b/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-config-setup.tsx index 028f2bbb84..0ba2309bf3 100644 --- a/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-config-setup.tsx +++ b/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-config-setup.tsx @@ -11,16 +11,19 @@ import { menusApi } from '../../../../lib/menus.api'; import { useNavToggle } from '../../../../lib/navigation-toggle.effect'; import { content } from '../../../../lib/rspack/content/rspack-config-setup'; import { pkg } from '../../../../lib/rspack/pkg'; +import { fetchGithubStarCount } from '../../../../lib/githubStars.api'; export default function RspackConfigSetup({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; pkg: ProcessedPackageMetadata; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -77,6 +80,7 @@ export default function RspackConfigSetup({ @@ -100,6 +104,9 @@ export async function getStaticProps() { props: { pkg, document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: [], menu: menusApi.getMenu('packages', ''), }, diff --git a/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-plugins.tsx b/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-plugins.tsx index 065c3d1834..6567ff04f5 100644 --- a/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-plugins.tsx +++ b/nx-dev/nx-dev/pages/packages/rspack/documents/rspack-plugins.tsx @@ -11,16 +11,19 @@ import { menusApi } from '../../../../lib/menus.api'; import { useNavToggle } from '../../../../lib/navigation-toggle.effect'; import { content } from '../../../../lib/rspack/content/rspack-plugin'; import { pkg } from '../../../../lib/rspack/pkg'; +import { fetchGithubStarCount } from '../../../../lib/githubStars.api'; export default function RspackPlugins({ document, menu, relatedDocuments, + widgetData, }: { document: ProcessedDocument; menu: MenuItem[]; pkg: ProcessedPackageMetadata; relatedDocuments: RelatedDocument[]; + widgetData: { githubStarsCount: number }; }): JSX.Element { const router = useRouter(); const { toggleNav, navIsOpen } = useNavToggle(); @@ -77,6 +80,7 @@ export default function RspackPlugins({ @@ -99,6 +103,9 @@ export async function getStaticProps() { props: { pkg, document, + widgetData: { + githubStarsCount: await fetchGithubStarCount(), + }, relatedDocuments: [], menu: menusApi.getMenu('packages', ''), }, diff --git a/nx-dev/ui-common/src/index.ts b/nx-dev/ui-common/src/index.ts index 1431e27616..0be0fe5c60 100644 --- a/nx-dev/ui-common/src/index.ts +++ b/nx-dev/ui-common/src/index.ts @@ -13,3 +13,4 @@ export * from './lib/nx-users-showcase'; export * from './lib/plugin-card'; export * from './lib/testimonial-card'; export * from './lib/typography'; +export * from './lib/github-star-widget'; diff --git a/nx-dev/ui-common/src/lib/github-star-widget.tsx b/nx-dev/ui-common/src/lib/github-star-widget.tsx new file mode 100644 index 0000000000..f38e51ab79 --- /dev/null +++ b/nx-dev/ui-common/src/lib/github-star-widget.tsx @@ -0,0 +1,58 @@ +import { sendCustomEvent } from '@nx/nx-dev/feature-analytics'; + +const GithubIcon = (props: any) => { + return ( + + {/*GitHub*/} + + + ); +}; + +export function GitHubStarWidget({ starsCount }: { starsCount: number }) { + const formatStars = (count: number) => { + if (count >= 1000) { + return (count / 1000).toFixed(1) + 'k'; + } else { + return count; + } + }; + + const handleClick = (eventAction: string) => { + sendCustomEvent( + eventAction, + 'githubstars-toc-sidebar', + 'githubstarswidget' + ); + }; + + return ( + + ); +}