import type { ShTangledRepoLanguages, ShTangledRepoTree, } from "@atcute/tangled"; import { type Params, useParams } from "@solidjs/router"; import { createMemo, createResource, createSignal, For, Match, Show, Switch, } from "solid-js"; import { SolidMarkdown } from "solid-markdown"; import { IconWithText } from "../../elements/icon_with_text"; import { languageColors } from "../../util/get_language"; import type { RepoLog } from "../../util/types"; import { useDid } from "./context"; import { Header } from "./main"; import { getRepoBranches, getRepoDefaultBranch, getRepoLanguages, getRepoLog, getRepoTree, } from "./main.data"; import "../../styles/markdown.css"; import { figureOutDid } from "../../util/handle"; export async function preloadRepoTree({ params }: { params: Params }) { const did = await figureOutDid(params.user); if (!did) return; getRepoTree(did, params.repo, params.ref, params.path); } export default function RepoTree() { const params = useParams(); const did = useDid(); const [defaultBranch] = createResource(did, async (did) => { const res = await getRepoDefaultBranch(did, params.repo); if (!res.ok) return; return res.data.name; }); const [tree] = createResource( () => { const d = did(); return d && ([d, params.repo, params.ref, params.path] as const); }, async ([d, repo, ref, path]) => { const res = await getRepoTree(d, repo, ref, path); if (!res.ok) return; return res.data; }, ); const [languages] = createResource(did, async (did) => { const res = await getRepoLanguages(did, params.repo, params.ref); if (!res.ok) return; return res.data.languages.sort((a, b) => b.percentage - a.percentage); }); const [logs] = createResource( () => { const d = did(); return d && ([d, params.repo, params.ref, params.path] as const); }, async ([d, repo, ref, path]) => { const res = await getRepoLog(d, repo, ref, path); if (!res.ok) return; return res.data as RepoLog; }, ); const [branchesAndTags] = createResource( () => { const d = did(); return d && ([d, params.repo, params.ref] as const); }, async ([d, repo, ref]) => { const resBranches = await getRepoBranches(d, repo, ref); if (!resBranches.ok) return; return resBranches.data as RepoLog; }, ); const [readme] = createResource(tree, async (tree) => { if (!tree.readme) return; return { contents: tree.readme.contents, type: tree.readme.filename.toLowerCase().endsWith(".md") ? "markdown" : "plaintext", } as const; }); const [filesInOrder] = createResource(tree, (tree) => { if (!tree.files) return; return tree.files.sort((a, b) => { if (!a.is_file === b.is_file) return !a.is_file ? -1 : 1; const aDot = a.name.startsWith("."); const bDot = b.name.startsWith("."); if (aDot !== bDot) return aDot ? -1 : 1; return a.name.localeCompare(b.name, undefined, { numeric: true }); }); }); const repoData = createMemo(() => { const db = defaultBranch(); const l = languages(); if (!(db && l)) return; return [db, l] as const; }); const pathData = createMemo(() => { const t = tree(); const f = filesInOrder(); const r = readme(); const l = logs(); if (!(t && f && r && l)) return; return [t, f, r, l] as const; }); return (
{([defaultBranch, languages]) => ( {([tree, files, readme, logs]) => (
)}
)}
); } function ReadmeCard(props: { path: string; readme: { type: "markdown" | "plaintext"; contents: string; }; }) { return (
`${props.path}${href}`} transformLinkUri={(href) => `${props.path}${href}`} renderingStrategy="memo" children={props.readme.contents} />
{props.readme.contents}
); } function LanguageLine(props: { languages: ShTangledRepoLanguages.Language[] }) { const [languageLineState, setLanguageLineState] = createSignal(false); const toggleLanguageLineState = () => setLanguageLineState(!languageLineState()); return (
{(language) => (
)}
{(language) => (
{language.name}{" "} {language.percentage}%
)}
); } function FileDirectory(props: { user: string; repo: string; files: ShTangledRepoTree.TreeEntry[]; tree: ShTangledRepoTree.$output; defaultBranch: string; }) { return (
.. {(file) => ( ); } function LogData(props: { user: string; repo: string; defaultBranch: string; files: ShTangledRepoTree.TreeEntry[]; logs: RepoLog; }) { return ( <>
{props.logs.total}
{(commit) => { const hash = commit.Hash.map((num) => num.toString(16).padStart(2, "0"), ).join(""); return (
{commit.Message.slice(0, commit.Message.indexOf("\n"))} {hash.slice(0, 8)} {commit.Author.Name} {`${new Date(commit.Author.When).toLocaleDateString(undefined, { dateStyle: "short" })} at ${new Date(commit.Author.When).toLocaleTimeString()}`}
); }}
); }