"Ask AI about me"

This commit is contained in:
Oliver Bryan
2026-01-14 23:17:22 +00:00
parent 16d7ca20f5
commit 9b699d48be
5 changed files with 1737 additions and 263 deletions

1416
bun.lock Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -13,6 +13,7 @@
"@astrojs/react": "^4.3.0",
"@astrojs/vercel": "^8.2.7",
"@iconify-json/mdi": "^1.2.3",
"@iconify-json/simple-icons": "^1.2.66",
"@tailwindcss/vite": "^4.1.13",
"@types/react": "^19.1.12",
"@types/react-dom": "^19.1.9",

View File

@@ -0,0 +1,24 @@
---
import { Icon } from "astro-icon/components";
import { AI_SUMMARY_PROMPT } from "../lib/constants";
interface Props {
url: string; // anything that precedes the prompt: e.g. "https://ai.example.com/?prompt="
title: string;
icon: string;
}
const { url, title, icon } = Astro.props;
const fullUrl = url + encodeURIComponent(AI_SUMMARY_PROMPT);
---
<a
href={fullUrl}
target="_blank"
rel="noopener noreferrer"
class="text-[var(--ayu-gutter)] hover:text-[var(--ayu-accent)] transition-colors duration-150"
title={title}
>
<Icon name={icon} class="w-7 h-7" />
</a>

2
src/lib/constants.ts Normal file
View File

@@ -0,0 +1,2 @@
export const AI_SUMMARY_PROMPT =
"I am a recruiter, tell me about Oliver Bryan, a software developer. What would he bring to the table? Review his portfolio at ob248.com and summarize his key strengths, technical skills, and notable projects. What makes him stand out as a candidate?";

View File

@@ -1,9 +1,10 @@
---
import Layout from "../layouts/Layout.astro";
import { Icon } from "astro-icon/components";
import AIPrompt from "../components/AIPrompt.astro";
import ProjectListItem from "../components/ProjectListItem.astro";
import TimeSince from "../components/TimeSince.astro";
import { Icon } from "astro-icon/components";
import Layout from "../layouts/Layout.astro";
import { AI_SUMMARY_PROMPT } from "../lib/constants";
export interface ProjectMetadata {
title: string;
@@ -107,7 +108,39 @@ const sortedTags = Array.from(allTags).sort((a, b) => a.localeCompare(b));
</style>
<Layout currentPage={{ title: "home", path: "/" }}>
<h2 class="text-2xl font-600 text-ayu-green-500 mb-2">ABOUT</h2>
<div class="flex justify-between items-start mb-4">
<h2 class="text-2xl font-600 text-ayu-green-500">ABOUT</h2>
<div class="flex flex-col items-end gap-2">
<p class="text-ayu-gutter text-lg">Ask AI about me</p>
<div class="flex gap-4 items-center">
<AIPrompt
url="https://chat.openai.com/?q="
title="Ask ChatGPT"
icon="simple-icons:openai"
/>
<AIPrompt
url="https://claude.ai/new?q="
title="Ask Claude"
icon="simple-icons:claude"
/>
<div class="relative flex items-center">
<button
id="copy-prompt-btn"
class="text-[var(--ayu-gutter)] hover:text-[var(--ayu-accent)] transition-colors duration-150 cursor-pointer flex items-center"
title="Copy prompt to clipboard"
>
<Icon name="mdi:content-copy" class="w-7 h-7" />
</button>
<span
id="copy-tooltip"
class="absolute bottom-full left-1/2 -translate-x-1/2 mb-2 px-2 py-1 text-sm bg-[var(--ayu-popup)] text-[var(--ayu-fg)] border border-[var(--ayu-gutter-dim)] rounded opacity-0 pointer-events-none transition-opacity duration-150 whitespace-nowrap"
>
Copied to clipboard
</span>
</div>
</div>
</div>
</div>
<span class="flex flex-wrap gap-2 mb-2">
<a
href="https://github.com/hex248"
@@ -143,20 +176,20 @@ const sortedTags = Array.from(allTags).sort((a, b) => a.localeCompare(b));
<span class="text-ayu-red-500 font-500">Name: </span>Oliver Bryan
</li>
<li>
<span class="text-ayu-blue-500 font-500">Role: </span>Junior
Software Developer
<span class="text-ayu-blue-500 font-500">Role: </span>Junior Software
Developer
</li>
<li>
<span class="text-ayu-red-500 font-500">Education: </span>Final Year
Software Engineeering (BEng), University of Westminster (2024-2026)
</li>
<li>
<span class="text-ayu-blue-500 font-500">Experience: </span>7 years,
1 year in industry as a Junior Software Developer
<span class="text-ayu-blue-500 font-500">Experience: </span>7 years, 1
year in industry as a Junior Software Developer
</li>
<li>
<span class="text-ayu-red-500 font-500">Skills: </span>Web
Development, Game Development, Python, JavaScript, TypeScript
<span class="text-ayu-red-500 font-500">Skills: </span>Web Development,
Game Development, Python, JavaScript, TypeScript
</li>
<li>
<span class="text-ayu-blue-500 font-500">Age: </span>
@@ -241,10 +274,7 @@ const sortedTags = Array.from(allTags).sort((a, b) => a.localeCompare(b));
const tagName = tag.getAttribute("data-tag");
if (selectedTags.has(tagName || "")) {
tag.classList.add(selectedTagBg, selectedTagText);
tag.classList.remove(
unselectedTagBorder,
unselectedTagText
);
tag.classList.remove(unselectedTagBorder, unselectedTagText);
} else {
tag.classList.remove(selectedTagBg, selectedTagText);
tag.classList.add(unselectedTagBorder, unselectedTagText);
@@ -261,37 +291,22 @@ const sortedTags = Array.from(allTags).sort((a, b) => a.localeCompare(b));
.map((t) => t.trim()) || [];
const hasAllTags =
selectedTags.size === 0 ||
Array.from(selectedTags).every((tag) =>
projectTags.includes(tag)
);
Array.from(selectedTags).every((tag) => projectTags.includes(tag));
if (hasAllTags) {
(project as HTMLElement).style.display = "block";
const tagElements =
project.getElementsByClassName("project-tag");
const tagElements = project.getElementsByClassName("project-tag");
const matchingTags = Array.from(tagElements).filter(
(tagElement) =>
selectedTags.has(
(tagElement as HTMLElement).innerText
)
const matchingTags = Array.from(tagElements).filter((tagElement) =>
selectedTags.has((tagElement as HTMLElement).innerText)
);
Array.from(tagElements).forEach((tag) => {
tag.classList.remove(
miniSelectedTagBorder,
miniSelectedTagText
);
tag.classList.add(
miniUnselectedTagBorder,
miniUnselectedTagText
);
tag.classList.remove(miniSelectedTagBorder, miniSelectedTagText);
tag.classList.add(miniUnselectedTagBorder, miniUnselectedTagText);
});
matchingTags.forEach((tag) => {
tag.classList.add(
miniSelectedTagBorder,
miniSelectedTagText
);
tag.classList.add(miniSelectedTagBorder, miniSelectedTagText);
tag.classList.remove(
miniUnselectedTagBorder,
miniUnselectedTagText
@@ -319,4 +334,20 @@ const sortedTags = Array.from(allTags).sort((a, b) => a.localeCompare(b));
});
});
</script>
<script define:vars={{ AI_SUMMARY_PROMPT }}>
document
.getElementById("copy-prompt-btn")
?.addEventListener("click", async () => {
await navigator.clipboard.writeText(AI_SUMMARY_PROMPT);
const tooltip = document.getElementById("copy-tooltip");
if (tooltip) {
tooltip.style.opacity = "1";
setTimeout(() => {
tooltip.style.opacity = "0";
}, 1000);
}
});
</script>
</Layout>