Introduction: Why Secure and Log Your API?

Welcome back! So far, you have learned how to organize your backend code using a service layer and how to validate data in your Task Manager API. Now, it’s time to make your API more secure and easier to monitor.

APIs are often exposed to the internet, which means anyone can try to access them. Without security, someone could misuse your API or access sensitive data. Logging is also important because it helps you see what’s happening in your API — who is using it, when, and how. This is useful for debugging and for keeping your API safe.

In this lesson, you will learn how to:

  • Protect your API using an API key.
  • Log every request to your API for better monitoring.

By the end, your Task Manager API will be more secure, and you’ll have a record of every request made to it.

Your Current Backend Structure

Before adding logging and API key security, let’s review how your current backend is structured:

  • You have API routes under /api/tasks, which call functions from your taskService to interact with an in-memory array of tasks.
  • All task-related routes (GET, POST, PUT, PATCH, DELETE) are already implemented in route.ts files using the service layer.
  • Now, we’ll add middleware that runs before any of these routes are handled to:
    • Check for a valid API key in the request.
    • Log information about every request for debugging and security. This mirrors how real-world APIs typically handle request-level authentication and monitoring.
Adding API Key Authentication With Middleware

To protect your API, you can require clients to include a special key (an API key) in their requests. Only requests with the correct key will be allowed.

In Next.js, you can use middleware to check for this key. Here’s how you can do it:

Explanation:

  • The middleware function runs before your API routes.
  • It checks if the request path starts with /api/tasks. From the previous courses we know that we can change this logic to protect any other paths in your API — for example, if you add /api/admin in the future. For now, we're securing just the /api/tasks endpoints.
  • If it does, it looks for an x-api-key header in the request.
  • If the key is missing or incorrect, it returns a 401 Unauthorized response. In production, you'd typically use a longer and more secure key — and rotate it periodically. You may also want to log these unauthorized attempts for auditing and alerting.
  • If the key is correct, the request continues.

Storing the API Key:

You should never hard-code secrets in your code. Instead, use environment variables. In your .env.local file, add:

Logging API Requests

Logging helps you keep track of what’s happening in your API. You can log details like the time, method, path, user agent, and IP address of each request.

Let’s add logging to the middleware:

Explanation:

  • We create a log object with useful information about the request.
  • timestamp records when the request happened.
  • method is the HTTP method (GET, POST, etc.).
  • path is the URL path.
  • userAgent tells you what kind of client made the request.
  • ip is the client’s IP address.
  • We print this log to the console.

Example Output:

This log will appear in your server’s console every time a request is made.

Applying Middleware To API Routes Only

You may not want your middleware to run for every route in your app. Next.js lets you control this with a matcher configuration.

Add this to your middleware.ts:

Explanation:

  • The matcher tells Next.js to only run this middleware for routes that start with /api/.
  • This keeps your security and logging focused on your API, not your whole app.
Frontend Integration: Sending the API Key

Now that your backend expects an API key in every request to /api/tasks, let’s look at how the frontend connects to this.

In your UI, you have an input field that lets users provide the API key manually:

This input updates the apiKey state, which is then used in all task-related fetch functions. Here's how a typical function looks:

This function does three things:

  • Checks if the API key is set — if not, it logs an error and stops the request.
  • Sends the request with the API key in the x-api-key header.
  • Logs the response to the browser console or log area in your UI.

This same pattern is used across other handlers (handleCreate, handleUpdate, handleDelete, etc.).

🔒 This setup simulates how authenticated APIs are used in the real world — the client includes a secret token (in this case, the API key), and the server validates it via middleware.

🧪 You can test different behaviors by:

  • Leaving the input blank → should trigger "Please provide the API key" warning.
  • Entering an incorrect key → should trigger a 401 Unauthorized response from the backend.
  • Entering the correct key → should result in a + console log from middleware.
Summary And Next Steps

In this lesson, you learned how to:

  • Secure your Task Manager API using an API key and middleware.
  • Log important details about every API request.
  • Apply middleware only to your API routes using the matcher config.

These steps make your API safer and easier to monitor. Now, you are ready to practice these skills in the exercises that follow. Since this is the last lesson of the course, congratulations on making it to the end! You have built a solid foundation in backend development with Next.js. Keep experimenting and building — your journey as a developer is just beginning!

Sign up
Join the 1M+ learners on CodeSignal
Be a part of our community of 1M+ users who develop and demonstrate their skills on CodeSignal