Skip to content

Commit

Permalink
feat: fetch linked pages
Browse files Browse the repository at this point in the history
  • Loading branch information
rob-at-airwalk committed Jun 15, 2024
1 parent 7833bfd commit c22f820
Show file tree
Hide file tree
Showing 6 changed files with 166 additions and 64 deletions.
22 changes: 16 additions & 6 deletions src/_components/Layouts/ContentViewer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ import type { ContentItem, RelatedContent } from '@/lib/Types';
import { loadMDX } from './lib/loadMDX';
// import { mdComponents } from '../../constants/mdxProvider.js';
const logger = getLogger().child({ namespace: 'ContentViewer' });
logger.level = 'error';
logger.level = 'debug';

type Contributor = {
authorName: string;
Expand Down Expand Up @@ -92,6 +92,19 @@ export function ContentViewer({
router.push(`${currentPath}/print`);
}

function handleContentChange(callback: any) {
// add '/related_content/' and the callback file to the path
router.push(`${currentPath}/related_content/${callback}`);
}

function handlePageReset() {
// reset the path to the current path before /related_content
const rootPath = currentPath.split('/related_content')[0];
if (rootPath) {
router.push(rootPath);
}
}

if (loading) {
return <ContentSkeleton topBarHeight={topBarHeight} />;
}
Expand Down Expand Up @@ -143,12 +156,9 @@ export function ContentViewer({
<ContentMenu
content={relatedContent}
context={context}
handleContentChange={() => {}}
handlePageReset={() => {}}
handleContentChange={(callback) => handleContentChange(callback)}
handlePageReset={() => handlePageReset()}
loading={false}
// handleContentChange={handleContentChange}
// handlePageReset={handlePageReset}
// file={context.file}
/>
{/* {sideComponent && <SideComponent />} */}
{frontmatter?.tableOfContents && (
Expand Down
6 changes: 1 addition & 5 deletions src/_components/Layouts/lib/getTiles.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import type {
FileContent,
FrontMatter,
GitHubFile,
MatterData,
} from '@/lib/Types';

const logger = getLogger().child({ module: 'getTiles' });
Expand All @@ -25,11 +26,6 @@ interface Tile {
[key: string]: any;
}

interface MatterData {
title: string;
[key: string]: Date | string;
}

export async function getTiles(config: ContentItem): Promise<{
loading: boolean;
error: Error | null | unknown;
Expand Down
5 changes: 4 additions & 1 deletion src/_components/Layouts/lib/mdxComponents.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,10 @@ const components = {
showLineNumbers={!!language}
// customStyle={{ overflow: 'clip', fontSize: '0.75rem', whiteSpace: 'pre-wrap' }}
customStyle={{
display: language ? 'block' : 'inline',
// display: language ? 'block' : 'inline',
display: 'block',
overflow: 'clip',
whiteSpace: 'pre-wrap',
...(language
? { fontSize: '0.75rem' }
: { background: 'unset', padding: 'unset', fontSize: '0.85rem' }),
Expand Down
2 changes: 1 addition & 1 deletion src/app/api/content/github/route.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ export async function GET(req: NextRequest) {

// return NextResponse.json({ files });
// }
const data = await getFileContent(owner, repo, branch, filepath);
const data = await getFileContent({ owner, repo, branch, path: filepath });
const extension = path.extname(filepath);
const contentType = mime.lookup(extension) || 'application/octet-stream';
// logger.info(`[GET /api/content/github][data]: ${util.inspect(data)}`);
Expand Down
65 changes: 61 additions & 4 deletions src/app/docs/[[...path]]/page.tsx
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@

import type { Metadata } from 'next'
import matter from 'gray-matter';

import React from "react";
import { IndexTiles, LandingPage, MenuWrapper, ContentViewer, ContentLoader, ContentPrint } from "@/components/Layouts";
import { siteConfig } from "../../../../site.config";
import { notFound } from "next/navigation";
import { getFileContent } from "@/lib/Github";
import { getLogger } from '@/lib/Logger';
import type { ContentItem } from '@/lib/Types';
import type { ContentItem, MatterData } from '@/lib/Types';
import { loadMenu, nestMenu } from '@/lib/Content/loadMenu';
const logger = getLogger().child({ namespace: 'docs/page' });
logger.level = 'error';
Expand All @@ -16,6 +17,47 @@ export const metadata: Metadata = {
description: "Airview AI",
};


async function checkFrontmatter(content: string, context: ContentItem) {
const matterData = matter(content, {
excerpt: false,
}).data as MatterData;
if (matterData) {
Object.keys(matterData).forEach((key) => {
if (
matterData &&
matterData[key] &&
matterData[key] instanceof Date
) {
matterData[key] = (matterData[key] as Date).toISOString();
}
});
}
if (matterData && matterData.external_repo && matterData.external_owner && matterData.external_path && matterData.git_provider) {
const { external_repo, external_owner, external_path } = matterData;
const owner = external_owner as string;
const repo = external_repo as string;
const branch = context.branch
const file = external_path as string;
let pageContent;
try {
pageContent = await getFileContent({owner, repo, path: file});
} catch (error) {
logger.error({ msg: 'checkFrontmatter: ', error});
}
let linkedContent = "";
if (pageContent && pageContent.content ) {
linkedContent = pageContent?.content
? Buffer.from(pageContent.content).toString()
: "";
}
return { content: linkedContent, context: { ...context, owner, repo, branch, file } };

} else {
return { content, context}
}
}

export default async function Page({
params,
}: {
Expand All @@ -33,7 +75,18 @@ export default async function Page({
path = path.slice(0, -1);
isPrint = true;
}
const file = path.join("/") as string;

let file = '';

// if 'related_config' is somewhere in the path, then the file is the last element in the path
if (path.includes('related_content')) {
// join all the parts after related_config
file = path.slice(path.indexOf('related_content') + 1).join("/") as string;
} else {
file = path.join("/") as string;
}

// const file = path.join("/") as string;
let pageContent;
let pageContentText;
let loading = false;
Expand Down Expand Up @@ -81,13 +134,17 @@ export default async function Page({

if (contentConfig?.owner && contentConfig?.repo && contentConfig?.branch && file) {
const { owner, repo, branch } = contentConfig;
pageContent = await getFileContent(owner, repo, branch, file);
pageContent = await getFileContent({owner, repo, path: file, branch});
if (pageContent && pageContent.content ) {
pageContentText = pageContent?.content
? Buffer.from(pageContent.content).toString()
: "";
}

const { content: linkedPageContentText, context } = await checkFrontmatter(pageContentText || '', contentConfig); // check for frontmatter context
pageContentText = linkedPageContentText;

logger.debug({ msg: 'context: ', context});


const content = await loadMenu(siteConfig, menuConfig(contentConfig));
Expand All @@ -113,7 +170,7 @@ export default async function Page({
menuStructure={menuStructure}
loading={loading}
context={contentConfig}>
<ContentViewer pageContent={pageContentText} contributors={pageContent.contributors} context={ contentConfig } loading={loading} relatedContent={content.relatedContent}/>
<ContentViewer pageContent={pageContentText} contributors={pageContent.contributors} context={ contentConfig } loading={loading} relatedContent={content.relatedContent} />
</MenuWrapper>
</main>
);
Expand Down
130 changes: 83 additions & 47 deletions src/lib/Github.ts
Original file line number Diff line number Diff line change
Expand Up @@ -255,13 +255,21 @@ async function getCachedFileContent(
return null;
}

async function getGitHubFileContent(
owner: string,
repo: string,
branch: string,
path: string,
branchShaParam: string | undefined = undefined,
): Promise<{
interface GitHubFileContentOptions {
owner: string;
repo: string;
path: string;
branchShaParam?: string;
branch?: string;
}

async function getGitHubFileContent({
owner,
repo,
path,
branchShaParam,
branch,
}: GitHubFileContentOptions): Promise<{
content: Buffer | undefined;
encoding: string;
contributors: { authorName: string; authorDate: string }[];
Expand All @@ -279,26 +287,41 @@ async function getGitHubFileContent(
branchShaParam,
});
let branchSha = null;
if (!branchShaParam) {
if (!branchShaParam && branch) {
branchSha = await getBranchSha(owner, repo, branch);
} else {
} else if (branchShaParam) {
branchSha = branchShaParam;
}
let response;
try {
response = (await gitHubInstance.repos.getContent({
owner,
repo,
path,
ref: branchSha,
})) as {
data: {
encoding: string;
sha: string;
content?: string;
download_url?: string;
if (branchSha) {
response = (await gitHubInstance.repos.getContent({
owner,
repo,
path,
ref: branchSha,
})) as {
data: {
encoding: string;
sha: string;
content?: string;
download_url?: string;
};
};
} else {
response = (await gitHubInstance.repos.getContent({
owner,
repo,
path,
})) as {
data: {
encoding: string;
sha: string;
content?: string;
download_url?: string;
};
};
};
}
} catch (error: any) {
logger.error({
function: 'getGitHubFileContent',
Expand Down Expand Up @@ -438,15 +461,24 @@ async function getGitHubFileContent(
return null;
}
}

interface FileContentOptions {
owner: string;
repo: string;
path: string;
fileSha?: string;
branchSha?: string;
branch?: string;
}
// Function to get a file content
export async function getFileContent(
owner: string,
repo: string,
branch: string,
path: string,
fileSha: string | undefined = undefined,
branchSha: string | undefined = undefined,
): Promise<{
export async function getFileContent({
owner,
repo,
path,
fileSha,
branchSha,
branch,
}: FileContentOptions): Promise<{
content: Buffer | undefined;
encoding: string;
contributors: {
Expand All @@ -457,25 +489,29 @@ export async function getFileContent(
// if the SHA is passed, this is a specific revision of a file.
// if not, pull back the generic revision of the file, stored with the branch sha instead.

const cachedContent = await getCachedFileContent(
owner,
repo,
branch,
path,
fileSha,
);
// logger.info(`github:getFileContent:getCachedFileContent ${cachedContent}`);
if (cachedContent) {
logger.info(`[GitHub][getGitHubFileContent][Cache/Hit]: ${path}`);
return cachedContent;
if (branch) {
const cachedContent = await getCachedFileContent(
owner,
repo,
branch,
path,
fileSha,
);
// logger.info(`github:getFileContent:getCachedFileContent ${cachedContent}`);
if (cachedContent) {
logger.info(`[GitHub][getGitHubFileContent][Cache/Hit]: ${path}`);
return cachedContent;
}
const file = await getGitHubFileContent({
owner,
repo,
path,
branchShaParam: branchSha,
branch,
});
return file;
}
const file = await getGitHubFileContent(owner, repo, branch, path, branchSha);

// const unencodedContent = Buffer.from(
// file?.content?.toString() || '',
// 'binary',
// );

const file = await getGitHubFileContent({ owner, repo, path });
return file;
}

Expand Down

0 comments on commit c22f820

Please sign in to comment.