Next.js application using TypeScript and Prisma blog categories.

Jun 04, 202455 mins read

blog-327070-1280.jpg

Define Prisma Schema
Ensure your Prisma schema includes a model for BlogCategory.

// schema.prisma
model BlogCategory {
  id           Int      @id @default(autoincrement())
  categoryName String
  createdAt    DateTime @default(now())
  updatedAt    DateTime @updatedAt
}

 

2. Create Controller Function
Implement a controller function to handle fetching and searching blog categories. Place this in a file like controllers/blogCategoryController.ts.

// controllers/blogCategoryController.ts
import { PrismaClient } from '@prisma/client';

const prisma = new PrismaClient();

export async function getBlogCategories(search: string | null = null) {
  if (search) {
    return prisma.blogCategory.findMany({
      where: { categoryName: { contains: search, mode: 'insensitive' } },
      orderBy: { categoryName: 'asc' },
    });
  } else {
    return prisma.blogCategory.findMany({
      orderBy: { categoryName: 'asc' },
    });
  }
}

 

3. Set up API Route
Create an API route to handle the GET request for fetching and searching blog categories. Place this in pages/api/blog-categories.ts.

// pages/api/blog-categories.ts
import type { NextApiRequest, NextApiResponse } from 'next';
import { getBlogCategories } from '@/app/server/controllers/blogCategoryController';

export default async function handler(req: NextApiRequest, res: NextApiResponse) {
  if (req.method === 'GET') {
    const { search } = req.query;

    try {
      const categories = await getBlogCategories(search ? String(search) : null);
      res.status(200).json({ categories });
    } catch (error) {
      console.error(error);
      res.status(500).json({ error: 'Internal Server Error' });
    }
  } else {
    res.setHeader('Allow', ['GET']);
    res.status(405).end(`Method ${req.method} Not Allowed`);
  }
}

 

4. Create View (Next.js Page)
Implement a Next.js page to display and search blog categories. Place this in pages/blog-categories/index.tsx.

// pages/blog-categories/index.tsx
import { useState, useEffect } from 'react';
import axios from 'axios';

const BlogCategoriesPage = () => {
  const [categories, setCategories] = useState([]);
  const [search, setSearch] = useState('');
  const [sortSearch, setSortSearch] = useState('');

  useEffect(() => {
    axios.get('/api/blog-categories', { params: { search: sortSearch } })
      .then(response => {
        setCategories(response.data.categories);
      })
      .catch(error => {
        console.error('Error fetching categories:', error);
      });
  }, [sortSearch]);

  const handleSearch = (e: React.FormEvent) => {
    e.preventDefault();
    setSortSearch(search);
  };

  return (
    <div>
      <h1>Blog Categories</h1>
      <form onSubmit={handleSearch}>
        <input
          type=text
          value={search}
          onChange={(e) => setSearch(e.target.value)}
          placeholder="Search categories"
        />
        <button type=submit>Search</button>
      </form>
      <ul>
        {categories.map((category: { id: number, categoryName: string }) => (
          <li key={category.id}>{category.categoryName}</li>
        ))}
      </ul>
    </div>
  );
};

export default BlogCategoriesPage;

 

Summary
Controller: The getBlogCategories function in controllers/blogCategoryController.ts handles fetching and searching blog categories.
API Route: The API route in pages/api/blog-categories.ts handles the GET request for fetching and searching blog categories.
View: The form in pages/blog-categories/index.tsx allows users to search and display blog categories.
This setup ensures that your Next.js application can handle fetching and searching blog categories while maintaining a clean MVC structure. Adjust the code as needed to fit your specific requirements.

Next.js application using TypeScript and Prisma, you need to handle form submission, validate the input, create a new blog category, and save it to the database.

1. Define Prisma Schema
Ensure your Prisma schema includes a model for BlogCategory.

// schema.prisma
model BlogCategory {
  id           Int      @id @default(autoincrement())
  categoryName String
  slug         String
  createdAt    DateTime @default(now())
  updatedAt    DateTime @updatedAt
}

 

2. Create Controller Function
Implement a controller function to handle creating a new blog category. Place this in a file like controllers/blogCategoryController.ts.

// controllers/blogCategoryController.ts
import { PrismaClient } from '@prisma/client';

const prisma = new PrismaClient();

export async function createBlogCategory(categoryName: string) {
  const slug = categoryName.toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/(^-|-$)/g, '');

  return prisma.blogCategory.create({
    data: {
      categoryName,
      slug,
    },
  });
}

 

3. Set up API Route
Create an API route to handle the POST request for creating a new blog category. Place this in pages/api/blog-categories.ts.

// pages/api/blog-categories.ts
import type { NextApiRequest, NextApiResponse } from 'next';
import { createBlogCategory } from '@/app/server/controllers/blogCategoryController';

export default async function handler(req: NextApiRequest, res: NextApiResponse) {
  if (req.method === 'POST') {
    const { categoryName } = req.body;

    if (!categoryName || typeof categoryName !== 'string' || categoryName.length > 255) {
      return res.status(400).json({ error: 'Category name is required and must be less than 255 characters.' });
    }

    try {
      const category = await createBlogCategory(categoryName);
      res.status(201).json({ category });
    } catch (error) {
      console.error(error);
      res.status(500).json({ error: 'Internal Server Error' });
    }
  } else {
    res.setHeader('Allow', ['POST']);
    res.status(405).end(`Method ${req.method} Not Allowed`);
  }
}

 

4. Create View (Next.js Page)
Implement a form in a Next.js page to allow users to create new blog categories. Place this in pages/blog-categories/new.tsx.

// pages/blog-categories/new.tsx
import { useState } from 'react';
import axios from 'axios';
import { useRouter } from 'next/router';

const NewBlogCategoryPage = () => {
  const [categoryName, setCategoryName] = useState('');
  const router = useRouter();

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    try {
      await axios.post('/api/blog-categories', { categoryName });
      alert('Blog category has been created successfully');
      router.push('/blog-categories');
    } catch (error) {
      console.error('Error creating category:', error);
      alert('Failed to create category');
    }
  };

  return (
    <div>
      <h1>Create New Blog Category</h1>
      <form onSubmit={handleSubmit}>
        <div>
          <label htmlFor="categoryName">Category Name</label>
          <input
            type=text
            id="categoryName"
            value={categoryName}
            onChange={(e) => setCategoryName(e.target.value)}
            required
            maxLength={255}
          />
        </div>
        <button type=submit>Create Category</button>
      </form>
    </div>
  );
};

export default NewBlogCategoryPage;

 

Summary
Controller: The createBlogCategory function in controllers/blogCategoryController.ts handles creating a new blog category.
API Route: The API route in pages/api/blog-categories.ts handles the POST request for creating a new blog category.
View: The form in pages/blog-categories/new.tsx allows users to submit new blog categories.
This setup ensures that your Next.js application can handle the creation of new blog categories while maintaining a clean MVC structure. Adjust the code as needed to fit your specific requirements.

Next.js application using TypeScript and Prisma, you need to handle form submission, validate the input, update the blog category, and save it to the database

1. Define Prisma Schema
Ensure your Prisma schema includes a model for BlogCategory.

// schema.prisma
model BlogCategory {
  id           Int      @id @default(autoincrement())
  categoryName String
  slug         String
  createdAt    DateTime @default(now())
  updatedAt    DateTime @updatedAt
}

 

2. Create Controller Function
Implement a controller function to handle updating a blog category. Place this in a file like controllers/blogCategoryController.ts.

// controllers/blogCategoryController.ts
import { PrismaClient } from '@prisma/client';

const prisma = new PrismaClient();

export async function updateBlogCategory(id: number, categoryName: string) {
  const slug = categoryName.toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/(^-|-$)/g, '');

  return prisma.blogCategory.update({
    where: { id },
    data: {
      categoryName,
      slug,
    },
  });
}

 

3. Set up API Route
Create an API route to handle the PUT request for updating a blog category. Place this in pages/api/blog-categories/[id].ts.

// pages/api/blog-categories/[id].ts
import type { NextApiRequest, NextApiResponse } from 'next';
import { updateBlogCategory } from '@/app/server/controllers/blogCategoryController';

export default async function handler(req: NextApiRequest, res: NextApiResponse) {
  const { id } = req.query;

  if (req.method === 'PUT') {
    const { categoryName } = req.body;

    if (!categoryName || typeof categoryName !== 'string' || categoryName.length > 255) {
      return res.status(400).json({ error: 'Category name is required and must be less than 255 characters.' });
    }

    try {
      const category = await updateBlogCategory(Number(id), categoryName);
      res.status(200).json({ category });
    } catch (error) {
      console.error(error);
      res.status(500).json({ error: 'Internal Server Error' });
    }
  } else {
    res.setHeader('Allow', ['PUT']);
    res.status(405).end(`Method ${req.method} Not Allowed`);
  }
}

 

4. Create View (Next.js Page)
Implement a form in a Next.js page to allow users to update blog categories. Place this in pages/blog-categories/[id]/edit.tsx.

// pages/blog-categories/[id]/edit.tsx
import { useState, useEffect } from 'react';
import axios from 'axios';
import { useRouter } from 'next/router';

const EditBlogCategoryPage = () => {
  const router = useRouter();
  const { id } = router.query;
  const [categoryName, setCategoryName] = useState('');

  useEffect(() => {
    if (id) {
      axios.get(`/api/blog-categories/${id}`)
        .then(response => {
          const { categoryName } = response.data.category;
          setCategoryName(categoryName);
        })
        .catch(error => {
          console.error('Error fetching category:', error);
        });
    }
  }, [id]);

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault();
    try {
      await axios.put(`/api/blog-categories/${id}`, { categoryName });
      alert('Blog category has been updated successfully');
      router.push('/blog-categories');
    } catch (error) {
      console.error('Error updating category:', error);
      alert('Failed to update category');
    }
  };

  return (
    <div>
      <h1>Edit Blog Category</h1>
      <form onSubmit={handleSubmit}>
        <div>
          <label htmlFor="categoryName">Category Name</label>
          <input
            type=text
            id="categoryName"
            value={categoryName}
            onChange={(e) => setCategoryName(e.target.value)}
            required
            maxLength={255}
          />
        </div>
        <button type=submit>Update Category</button>
      </form>
    </div>
  );
};

export default EditBlogCategoryPage;

 

Summary
Controller: The updateBlogCategory function in controllers/blogCategoryController.ts handles updating a blog category.
API Route: The API route in pages/api/blog-categories/[id].ts handles the PUT request for updating a blog category.
View: The form in pages/blog-categories/[id]/edit.tsx allows users to submit updates to blog categories.
This setup ensures that your Next.js application can handle the update of blog categories while maintaining a clean MVC structure. Adjust the code as needed to fit your specific requirements.

Next.js application using TypeScript and Prisma, you need to handle the deletion of a blog category

// schema.prisma
model BlogCategory {
  id           Int      @id @default(autoincrement())
  categoryName String
  slug         String
  createdAt    DateTime @default(now())
  updatedAt    DateTime @updatedAt
}

 

2. Create Controller Function
Implement a controller function to handle deleting a blog category. Place this in a file like controllers/blogCategoryController.ts.

// controllers/blogCategoryController.ts
import { PrismaClient } from '@prisma/client';

const prisma = new PrismaClient();

export async function deleteBlogCategory(id: number) {
  return prisma.blogCategory.delete({
    where: { id },
  });
}

 

3. Set up API Route
Create an API route to handle the DELETE request for deleting a blog category. Place this in pages/api/blog-categories/[id].ts.

// pages/api/blog-categories/[id].ts
import type { NextApiRequest, NextApiResponse } from 'next';
import { deleteBlogCategory } from '@/app/server/controllers/blogCategoryController';

export default async function handler(req: NextApiRequest, res: NextApiResponse) {
  const { id } = req.query;

  if (req.method === 'DELETE') {
    try {
      await deleteBlogCategory(Number(id));
      res.status(200).json({ message: 'Blog category deleted successfully' });
    } catch (error) {
      console.error(error);
      res.status(500).json({ error: 'Internal Server Error' });
    }
  } else {
    res.setHeader('Allow', ['DELETE']);
    res.status(405).end(`Method ${req.method} Not Allowed`);
  }
}

 

4. Create View (Next.js Page)
Implement a page in Next.js to display and delete blog categories. Place this in pages/blog-categories/index.tsx.

// pages/blog-categories/index.tsx
import { useState, useEffect } from 'react';
import axios from 'axios';
import { useRouter } from 'next/router';

const BlogCategoriesPage = () => {
  const [categories, setCategories] = useState([]);
  const router = useRouter();

  useEffect(() => {
    fetchCategories();
  }, []);

  const fetchCategories = async () => {
    try {
      const response = await axios.get('/api/blog-categories');
      setCategories(response.data.categories);
    } catch (error) {
      console.error('Error fetching categories:', error);
    }
  };

  const handleDelete = async (id: number) => {
    if (confirm('Are you sure you want to delete this category?')) {
      try {
        await axios.delete(`/api/blog-categories/${id}`);
        alert('Blog category deleted successfully');
        fetchCategories();
      } catch (error) {
        console.error('Error deleting category:', error);
        alert('Failed to delete category');
      }
    }
  };

  return (
    <div>
      <h1>Blog Categories</h1>
      <ul>
        {categories.map((category: { id: number, categoryName: string }) => (
          <li key={category.id}>
            {category.categoryName}
            <button onClick={() => handleDelete(category.id)}>Delete</button>
          </li>
        ))}
      </ul>
    </div>
  );
};

export default BlogCategoriesPage;

 

Summary
Controller: The deleteBlogCategory function in controllers/blogCategoryController.ts handles deleting a blog category.
API Route: The API route in pages/api/blog-categories/[id].ts handles the DELETE request for deleting a blog category.
View: The page in pages/blog-categories/index.tsx allows users to delete blog categories.
This setup ensures that your Next.js application can handle the deletion of blog categories while maintaining a clean MVC structure. Adjust the code as needed to fit your specific requirements.

Share
Newsletter

Subscribe our newsletter