This project demonstrates how to securely call an external API from a Next.js app using the ensure_api
module for request preparation and decryption.
- Node.js
- Next.js
- Clone the repository:
git clone <repository_url> cd <repository_directory>
- Install dependencies:
npm install
The loadPosts
function prepares a fetch request using ensure_api
and sends it to the API route.
import ensure_api from 'ensure_api';
export async function loadPosts() {
const requestPayload = await ensure_api.prepareFetchRequest(
"https://official-joke-api.appspot.com/random_joke",
{ method: 'GET', credentials: 'same-origin' },
{ 'Custom-Header': 'new-custom-value' }
);
const response = await fetch(`http://localhost:3000/api/request`, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ key: requestPayload }),
cache: 'no-store',
});
if (!response.ok) throw new Error(`HTTP error! status: ${response.status}`);
return response.json();
}
The API route at app/api/request/route.js
handles the POST request, decrypts it using ensure_api
, and fetches data from the external API.
import { NextResponse } from 'next/server';
import ensure_api from 'ensure_api';
export async function POST(request) {
try {
const body = await request.json();
const encryptedKey = body.key;
const decryptedRequest = ensure_api.decryptRequest(encryptedKey);
if (!decryptedRequest || !decryptedRequest.url || !decryptedRequest.method || !decryptedRequest.headers || !decryptedRequest.credentials) {
throw new Error('Decrypted request is missing required fields');
}
const headers = new Headers();
decryptedRequest.headers.forEach(([key, value]) => headers.append(key, value));
const fetchRequest = new Request(decryptedRequest.url, {
method: decryptedRequest.method,
headers: headers,
credentials: decryptedRequest.credentials,
body: JSON.stringify(decryptedRequest.body),
});
const fetchResponse = await fetch(fetchRequest);
if (!fetchResponse.ok) throw new Error(`HTTP error! status: ${fetchResponse.status}`);
const responseData = await fetchResponse.json();
return NextResponse.json(responseData, { status: 200 });
} catch (error) {
return NextResponse.json({ error: error.message }, { status: 500 });
}
}
To use the loadPosts
function in a component:
import React, { useEffect, useState } from 'react';
import { loadPosts } from './path/to/your/loadPostsFunction';
const ExampleComponent = () => {
const [data, setData] = useState(null);
useEffect(() => {
const fetchData = async () => {
try {
const result = await loadPosts();
setData(result);
} catch (error) {
console.error('Error fetching data:', error);
}
};
fetchData();
}, []);
if (!data) return <div>Loading...</div>;
return (
<div>
<h1>Random Joke</h1>
<p>{data.setup}</p>
<p>{data.punchline}</p>
</div>
);
};
export default ExampleComponent;
- Replace the mock decryption function in
route.js
with your actual decryption logic. - Adjust
prepareFetchRequest
and its usage according to yourensure_api
requirements.
This project is licensed under the ISC License. See the LICENSE file for details.