0

I have working nextjs app using prisma as ORM. I have this page: /somecats which connect to nextjs backend (/pages/api/categories). When I execute http://localhost:3000/api/requests), it not require authorize. I want this endpoint should be authorized. How can I do this in NextJS especially with next-connect?

I’ve tried this tutorial but it’s not working, still not authorized.

This is /pages/api/categories/index.js now and still not authorized:

import { getCategories, postCategory } from '../../../database/controller';
import { verify } from 'jsonwebtoken';

const handler = nc({
    onError: (err, req, res, next) => {
        console.error(err.stack);
        return res.status(500).end(err);
    },
    onNoMatch: (req, res, next) => {
        return res.status(404).end("Page is not found");
    },
}).use((req, res, next) => {
    req.userId = null;
    req.username = null;

    const { authorization } = req.headers;

    if (!authorization) {
        next();
    } else {
        verify(authorization, 'khidir-secret', (error, decoded) => {
            if (!error && decoded) {
                req.userId = decoded.userId;
                req.username = decoded.name;
            }

            next();
        });
    }
})

    .get(async (req, res) => getCategories(req, res))
    .post(async (req, res) => postCategory(req, res))

export default handler;

And also did this too:

//this is /lib/handler.ts
import { verify } from 'jsonwebtoken';
import { NextApiRequest, NextApiResponse } from 'next';
import nextConnect from 'next-connect';

export interface NextApiRequestExtended extends NextApiRequest {
  userId: number | null;
  username: string | null;
}

export default function getHandler() {
  return nextConnect<NextApiRequestExtended, NextApiResponse>({
  onError(error, req, res) {
    res.status(501).json({ error: `Sorry something Happened! ${error.message}` });
  },
  onNoMatch(req, res) {
    res.status(405).json({ error: `Method ${req.method} Not Allowed` });
  },
}).use((req, res, next) => {
  req.userId = null;
  req.username = null;

  const { authorization } = req.headers;

  if (!authorization) {
    next();
  } else {
    verify(authorization, 'khidir-secret', (error: any, decoded: any) => {
      if (!error && decoded) {
        req.userId = decoded.userId;
        req.username = decoded.name;
      }

      next();
    });
  }
})};

And call that handler with this:

// this is version2 of /pages/api/categories.js
import { getCategories, postCategory } from '../../../database/controller';
import getHandler from '../../../lib/handler';

export default getHandler()
    .get(async (req, res) => getCategories(req, res))
    .post(async (req, res) => postCategory(req, res));

Those codes are both working, BUT with NO Authorization. What should I do?

bandungeuy
  • 378
  • 4
  • 19

1 Answers1

-1

The code you have provided is already using authorization middleware in NextJS API backend. The authorization middleware extracts the authorization header from the request and verifies it using the verify method. If the authorization header is present and verified successfully, it sets the userId and username properties in the req object.

To use authorization, you need to pass the authorization header with a valid token while making a request to this API. For example, you can use the fetch API to make a request with the authorization header as follows:

const token = 'valid_token_here';
fetch('/api/categories', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': `Bearer ${token}`
  },
  body: JSON.stringify({ name: 'Category Name' })
})
.then(response => response.json())
.then(data => console.log(data))
.catch(error => console.error(error));

In the above example, the Authorization header is set with a Bearer token that is concatenated with the valid token value. This token will be verified by the middleware in the API backend and if it is valid, the userId and username properties will be set in the req object.

Note: The verify method used in the middleware is not defined in the code you provided. You need to import it from a library like jsonwebtoken to use it.