
Building a Modern Developer Portfolio with Next.js 15 and Tailwind CSS
Introduction
Creating a personal portfolio as a developer isn't just about listing your projects - it's about showcasing your capabilities, performance mindset, and understanding of modern web practices. In this post, I’ll walk you through how I built my portfolio using Next.js 15, Tailwind CSS, and a few more powerful tools.
🚀 Why I Chose Next.js 15 with App Router
With the introduction of the App Router in Next.js 13+, the framework became even more powerful for building modular and scalable applications. In version 15.3.2, the routing experience is smoother, and features like server components and layouts are stable and production-ready.
Key Highlights:
- Nested Routing: Easier management of pages and layout hierarchies.
- Server Components: Faster load times and smaller bundle sizes.
- SEO and ISR: Built-in support for static rendering and SEO optimizations.
app/
being the entry point for pages:
saket-portfolio/ ├── app/ │ ├── layout.js │ └── page.js
🎨 Styling with Tailwind CSS
Tailwind CSS was my go-to choice for styling because of its:
- Utility-first approach
- Responsive design utilities
- Dark mode support
- Ease of customization
tailwind.config.js
:
module.exports = { content: ["./app/**/*.{js,ts,jsx,tsx}", "./components/**/*.{js,ts,jsx,tsx}"], theme: { extend: {}, }, plugins: [], }
This setup ensures all components and pages are scanned for utility classes.
✨ Adding Motion with Framer
To bring life to the UI, I used Framer Motion. It allowed me to add clean, non-intrusive animations:
- Fade-ins on page load
- Slide-ins for sections
- Hover interactions for cards and buttons
Example usage in a Hero section:
<motion.div initial={{ opacity: 0 }} animate={{ opacity: 1 }} transition={{ duration: 1 }}> <h1>Hello, I'm Saket Singh 👋</h1> </motion.div>
🧩 Component-Driven Architecture
The site is designed with reusability and scalability in mind:
Hero
,Projects
,Experience
,Resume
, andPublications
are all self-contained components.- Each section reads from a corresponding data file (e.g.,
HeroData.js
,ProjectsData.js
), making content updates seamless.
📄 Resume Section with Embedded PDF
- Embedded an interactive PDF viewer for the resume using a dynamic PdfViewer component to enhance user experience and SEO.
- Included a sticky header and multiple responsive download buttons for accessibility across devices.
- Styled the layout with modern gradients, shadows, and animations using Tailwind CSS and Framer Motion.
- Improved time-on-site and user engagement with an in-page resume view instead of a forced download.
📝 Editable Content via Netlify CMS
To manage content dynamically, I integrated Netlify CMS:
- Markdown content for blogs resides in
/content/blog/
. - The CMS dashboard is deployed on a separate Netlify project (
netlify-cms-admin
) but commits directly to my main repo. - All blog posts are written in
.md
format and support preview before publishing.
CMS Config Snippet:
backend: name: git-gateway branch: main
This decoupled setup gives me the flexibility to scale or switch CMS anytime.
📱 Responsive by Default
- Tailwind's responsive design classes (
sm:
,md:
,lg:
) helped me build for mobile-first without extra media queries. - The entire site looks and feels great on devices of all sizes.
🌐 Deployed via Vercel
Deployment was frictionless:
- Connected the GitHub repo on Vercel.
- Default build settings worked out of the box.
- Automatic deployments on every
main
branch push. - Preview deployments for feature branches.
🧠 Key Takeaways
- Next.js App Router is a game-changer for scalable personal sites.
- Tailwind speeds up UI development without sacrificing quality.
- Framer Motion helps enhance user experience with subtle animations.
- Decoupling CMS from the main app makes management easier.
- Vercel + GitHub = dream deployment pipeline.
✍️ Up Next: In the next blog, we’ll dive into Integrating Netlify CMS with GitHub Repo in a Next.js Portfolio to enable a smooth, Git-based content workflow.