Vibe Code to codebykarun.com: Evolving with Series Support (Part 8)

10 min read
vibe codingui designfeature developmentiteration

Part 3 of 5 in Evolution & Growth • Previously: Your Guide to Vibe Coding

After launching Code by Karun with the foundation complete, I had multiple articles that formed a series. But they were just listed chronologically like any other posts. I wanted to make series more discoverable with a special card deck design that would stand out on the home page.

This article documents that conversation—showing how vibe coding works for iterating on an existing project, not just building from scratch.

The Initial Request

My starting point was simple:

"Let's make category for series type articles which should a card deck type tile keep this state maintainable"

Notice what I didn't specify:

  • How the data structure should work
  • Where to store series metadata
  • What "card deck" should look like exactly
  • How to make it maintainable

I just expressed the goal. Let's see how the conversation unfolded.

Step 1: Understanding the Current System

The AI started by examining the existing code:

  • How articles are structured (Article type)
  • How MDX frontmatter is parsed
  • What files exist in the series

This is a key vibe coding practice: Start by understanding what exists before building anything new.

Step 2: Designing the Data Model

The AI proposed changes to the type system:

export interface Article {
  // ... existing fields
  series?: string; // Series identifier (e.g., "vibe-coding-journey")
  seriesOrder?: number; // Order within the series (e.g., 1, 2, 3)
}

export interface Series {
  id: string;
  title: string;
  description: string;
  category: ArticleCategory;
  articles: Article[];
  totalArticles: number;
  firstPublished: string;
  lastPublished: string;
}

Why this worked:

  • Extends existing structure without breaking changes
  • Optional fields mean old articles still work
  • Clear, self-documenting field names

Step 3: The Maintainability Solution

Here's where it got clever. The AI created a single source of truth:

const SERIES_CONFIG: Record<string, { title: string; description: string }> = {
  "vibe-coding-journey": {
    title: "Building codebykarun.com: The Vibe Coding Journey",
    description: "A 7-part series documenting how I built my blog...",
  },
  // Add more series here as needed
};

Then articles just reference this:

---
title: "Your Article Title"
series: "vibe-coding-journey"
seriesOrder: 1
---

Why this is maintainable:

  1. Series metadata in one place
  2. Articles use simple references
  3. System automatically groups and sorts
  4. Adding new series = two simple steps

This is better than I initially imagined. I said "keep this state maintainable" and got a genuinely maintainable solution.

Step 4: The Card Deck Design

I asked for a "card deck type tile." The AI created a design with:

  • Layered background cards (the deck effect)
  • Series badge with icon
  • First 3 articles preview with numbered badges
  • "+N more articles" indicator
  • Hover effects
{/* Deck effect - layered cards in background */}
<div className="absolute top-1.5 left-1.5 right-1.5 h-full 
  bg-[var(--warm-100)] dark:bg-[var(--warm-100)] 
  rounded-xl -z-10 opacity-50" />
<div className="absolute top-3 left-3 right-3 h-full 
  bg-[var(--warm-50)] dark:bg-[var(--warm-50)] 
  rounded-xl -z-20 opacity-30" />

The layered absolute positioned divs create the stacked card effect without JavaScript or complex CSS.

Step 5: Iterating on Design

After seeing the result, I had feedback:

"It's too big make it smaller"

The AI reduced all spacing, font sizes, and padding:

  • p-6p-4 sm:p-5
  • var(--text-xl)var(--text-lg)
  • w-6 h-6 badges → w-5 h-5

Then another issue:

"Series episodes are not readable update text color to a lighter color"

First attempt used darker text. I clarified:

"Text visibility is still a challenge go lighter color not darker go towards white"

The AI adjusted to pure white for dark mode:

className="text-[var(--warm-900)] dark:text-white"

The lesson: Don't expect perfection on the first try. Vibe coding is a conversation. Quick iterations get you to the right solution faster than trying to specify everything upfront.

Step 6: Updating All Content

The AI then:

  1. Updated all 7 existing articles with series metadata
  2. Modified the MDX parser to read the new fields
  3. Created helper functions to query series
  4. Added the series section to the home page
  5. Updated documentation

All automatically, in one flow.

The Implementation Details

Here's what got built:

Data Layer (app/lib/articles.ts)

export function getAllSeries(): Series[] {
  const allArticles = getAllArticlesFromAllCategories();
  const seriesMap = new Map<string, Article[]>();

  // Group articles by series
  allArticles.forEach((article) => {
    if (article.series) {
      if (!seriesMap.has(article.series)) {
        seriesMap.set(article.series, []);
      }
      seriesMap.get(article.series)?.push(article);
    }
  });

  // Convert to Series objects with sorting
  // ...
}

Clean, functional approach. Groups articles, sorts them, builds the Series objects.

UI Component (app/components/SeriesCard.tsx)

The component is self-contained:

  • Handles category-specific colors
  • Shows deck effect
  • Responsive spacing
  • Hover states
  • Dark mode support

Home Page Integration

const allSeries = getAllSeries();

{allSeries.length > 0 && (
  <section>
    <h2>Featured Series</h2>
    <div className="grid grid-cols-1 lg:grid-cols-2 gap-6">
      {allSeries.map((series) => (
        <SeriesCard key={series.id} {...series} />
      ))}
    </div>
  </section>
)}

Only shows if series exist. Responsive grid. Simple and clean.

Documenting the Feature

I asked: "Add this to Blog authoring md"

The AI updated BLOG_AUTHORING.md with:

  • New frontmatter field documentation
  • Step-by-step series creation guide
  • Best practices
  • Real examples from the codebase
  • Troubleshooting tips

Now future me (or contributors) can easily create series.

What Made This Effective

1. High-Level Goals

I didn't specify implementation details. I said what I wanted, not how to build it.

Bad: "Create a React component called SeriesCard that takes props title, description, articles array..."

Good: "Make a card deck type tile for series that's maintainable"

2. Incremental Feedback

Each iteration was quick:

  • "Too big" → Smaller
  • "Not readable" → Lighter text
  • "Add to docs" → Documentation added

No need to get it perfect first try.

3. Context Awareness

The AI examined:

  • Existing article structure
  • Current MDX parsing
  • Design system variables
  • File locations

It integrated seamlessly with existing code instead of creating something separate.

4. Maintainability Focus

The SERIES_CONFIG pattern emerged from my requirement to "keep this state maintainable." It's genuinely easier to maintain than alternatives like:

  • Hardcoding series data in components
  • Duplicating metadata across articles
  • Complex database schemas

The Complete Feature Set

What we built in one conversation:

✅ Type system extensions (Article + Series interfaces)
✅ MDX parser updates
✅ Series configuration system
✅ Helper functions (getAllSeries, getSeriesById, etc.)
✅ SeriesCard component with card deck design
✅ Home page integration
✅ Responsive layouts
✅ Dark mode support
✅ Hover interactions
✅ Metadata for all 7 existing articles
✅ Complete documentation

Total time: About 15-20 minutes of back-and-forth conversation.

Lessons for Iterating on Existing Projects

Start Broad, Then Narrow

Begin with exploratory questions:

  • "How are articles structured?"
  • "Where is content parsed?"

Then get specific:

  • "Add series field to Article type"
  • "Update the parser"

Trust the Context

When working with an existing codebase, the AI can:

  • Match your existing patterns
  • Use your design system
  • Follow your naming conventions
  • Integrate with your structure

You don't have to specify these things.

Iterate Quickly

Don't try to get the design perfect in your first request:

  1. Get something working
  2. See what needs adjustment
  3. Make targeted changes
  4. Repeat until satisfied

This is faster than trying to specify everything upfront.

Think in Features, Not Files

I didn't say:

  • "Create a file called SeriesCard.tsx"
  • "Update articles.ts with these functions"
  • "Modify the home page like this"

I said:

  • "Make series discoverable"
  • "Use a card deck design"
  • "Keep it maintainable"

The AI figured out which files to create/modify.

The Maintainability Payoff

Adding a new series now takes two steps:

1. Add to config:

"new-series-id": {
  title: "Series Title",
  description: "Brief description",
}

2. Add to articles:

series: "new-series-id"
seriesOrder: 1

That's it. The system handles everything else:

  • Grouping articles
  • Sorting by order
  • Calculating counts
  • Displaying the card
  • All styling and interactions

When Vibe Coding Shines

This feature demonstrates when vibe coding is most powerful:

✅ Good Fit: Adding Features to Existing Projects

  • Clear existing patterns to follow
  • Well-defined component structure
  • Need to integrate seamlessly

✅ Good Fit: UI/UX Iterations

  • Quick visual adjustments
  • Responsive design tweaks
  • Color and spacing refinements

✅ Good Fit: Data Structure Extensions

  • Adding optional fields
  • Creating new types
  • Building helper functions

❌ Less Ideal: Complex Algorithms

  • Advanced data structures
  • Performance-critical code
  • Domain-specific logic

❌ Less Ideal: Architecture Decisions

  • Choosing state management
  • Database schema design
  • Security implementations

Reflections on the Process

What Surprised Me

The SERIES_CONFIG pattern was more elegant than what I had in mind. I was thinking about where to store series metadata, and the AI found a solution that's:

  • Simple (just a TypeScript object)
  • Maintainable (single source of truth)
  • Flexible (easy to extend)
  • Type-safe (TypeScript validates it)

What Required Iteration

The visual design took a few rounds:

  • Initial version was too large
  • Text contrast needed adjustment
  • Needed to go lighter, not darker, for dark mode

This is normal. Visual preferences are subjective and hard to specify perfectly upfront.

What Worked Immediately

  • Type system extensions
  • Data parsing
  • Helper functions
  • Documentation

The "code" parts worked first try. The "visual" parts needed iteration.

Key Takeaways

  1. Vibe coding works for iteration, not just creation

    • You can evolve existing projects
    • Context helps AI match your patterns
    • Integration is often seamless
  2. Maintainability can be conversational

    • Express the goal ("keep it maintainable")
    • Don't prescribe the solution
    • You might get something better than imagined
  3. Design is iterative by nature

    • First version rarely perfect
    • Quick adjustments are fine
    • Feedback loop is fast
  4. Documentation matters

    • Ask for docs to be updated
    • Makes features usable long-term
    • Helps future you understand decisions
  5. High-level goals > detailed specs

    • "Card deck design" was enough
    • Implementation details emerged
    • Results matched intent

Try It Yourself

If you have an existing project, try adding a feature through conversation:

  1. Describe the goal without specifying implementation
  2. Let the AI explore your existing code
  3. Review the proposal and give feedback
  4. Iterate on details until it's right
  5. Don't forget docs for future reference

The code from this conversation is live on Code by Karun. The series cards you see on the home page? That's exactly what emerged from this collaborative process.

Conclusion

Building codebykarun.com wasn't just about the initial launch. It's about continuing to evolve it through the same conversational approach.

This series feature—from concept to documentation—took one conversation. The resulting code is maintainable, the design is polished, and adding future series is trivial.

That's the power of vibe coding applied to real-world iteration.


👀 Sneak Peek: What's Next

After building the series feature, I realized we had a perfect opportunity to enhance SEO. With dedicated series pages showcasing multiple articles, we could implement rich structured data that would give search engines a complete understanding of the content hierarchy.

Coming in Part 9: I'll show you how I transformed the blog's SEO with JSON-LD structured data, dynamic metadata generation, and crawler-friendly markup—all through conversational development. You'll see how to make your content not just visible, but fully understood by search engines.

Continue to: SEO Enhancement with Structured Data