Harden nginx: add CSP, HSTS, Referrer-Policy and Permissions-Policy; include image/svg+xml in gzip types; set X-Content-Type-Options on static assets; change try_files to return =404. Add Nav component and wire into BaseLayout; add About and Projects pages with projects.json, an initial blog post, and small layout/padding adjustments (removed redundant back links).
This commit is contained in:
@@ -0,0 +1,89 @@
|
||||
---
|
||||
const currentPath = Astro.url.pathname;
|
||||
|
||||
const links = [
|
||||
{ href: "/", label: "home" },
|
||||
{ href: "/about", label: "about" },
|
||||
{ href: "/projects", label: "projects" },
|
||||
{ href: "/blog", label: "blog" },
|
||||
];
|
||||
|
||||
function isActive(href: string, current: string): boolean {
|
||||
if (href === "/") return current === "/";
|
||||
return current.startsWith(href);
|
||||
}
|
||||
---
|
||||
|
||||
<nav class="nav" aria-label="Main navigation">
|
||||
<div class="nav-inner">
|
||||
{links.map((link, i) => (
|
||||
<>
|
||||
{i > 0 && <span class="nav-sep" aria-hidden="true">·</span>}
|
||||
<a
|
||||
href={link.href}
|
||||
class:list={["nav-link", { active: isActive(link.href, currentPath) }]}
|
||||
aria-current={isActive(link.href, currentPath) ? "page" : undefined}
|
||||
>
|
||||
~/{link.label}
|
||||
</a>
|
||||
</>
|
||||
))}
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<style>
|
||||
.nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
z-index: 100;
|
||||
padding: var(--space-sm) var(--space-md);
|
||||
background: rgba(30, 30, 46, 0.85);
|
||||
backdrop-filter: blur(8px);
|
||||
border-bottom: 1px solid var(--color-surface);
|
||||
}
|
||||
|
||||
.nav-inner {
|
||||
max-width: 700px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: var(--space-xs);
|
||||
font-size: 0.85rem;
|
||||
}
|
||||
|
||||
.nav-sep {
|
||||
color: var(--color-surface);
|
||||
user-select: none;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--color-text-dim);
|
||||
text-decoration: none;
|
||||
padding: 2px 4px;
|
||||
border-radius: 3px;
|
||||
transition: color 0.2s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
color: var(--color-accent-bright);
|
||||
}
|
||||
|
||||
.nav-link.active {
|
||||
color: var(--color-accent);
|
||||
text-decoration: underline;
|
||||
text-underline-offset: 3px;
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.nav {
|
||||
padding: var(--space-xs) var(--space-sm);
|
||||
}
|
||||
|
||||
.nav-inner {
|
||||
font-size: 0.8rem;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user