Vous êtes sur la page 1sur 5

EPSI Bordeaux - B3 DEV FullStack - Services Web:

Communication et échanges de données - TIPS


NEXT.JS

Infos pratiques

Promotion: B3 Dev FS - EPSI Bordeaux - 2022/2023


Module: Atelier - BDOE622 - Services Web: Communication et échanges de données
Enseignant / Formateur: Julien Couraud
Contact: julien.couraud@reseau-cd.net

Tips Next.JS

Starter-kit

--> Utilisation du starter-kit "with-mongodb" sur le Github de Vercel Next.JS

https://github.com/vercel/next.js/tree/canary/examples/with-mongodb

--> Setup de la connexion à la base de données via le fichier '.env.local' en utilisant le "connection string" depuis MongoDB
Atlas.

Commandes

npm run dev

--> Si la connexion à la base de données MongoDB Atlas s'est correctement faite, vous devriez voir apparaître sur votre
localhost:3000 le message "Connected to MongoDB".

Ouvrir un endpoint API

--> Dans le dossiers 'pages', créez un dossier 'api'. A l'intérieur de ce dossier, toute l'arborescence proposée correspondra à
vos routes API.

Exemple d'accès à notre base de données

--> Prenons par exemple un endpoint 'api/likes' qui retourne toutes les ressources d'une collection 'likes' sur notre base de
données MongoDB.

// Fichier /pages/api/likes.js

import clientPromise from "../../lib/mongodb";

export default async function handler(req, res) {

const client = await clientPromise;


const db = client.db("ws-app-db");
const likes = await db.collection("likes").find({}).toArray();
res.json({ status: 200, data: likes });
}

--> Le resultat est visible lors d'un appel GET au endpoint http://localhost:3000/api/likes

Exemple d'accès à l'API 'TheMovieDB'

--> Dans le cadre du projet, il faut commencer par le endpoint '/api/discover' qui renvoie dans un premier temps directement
les films depuis l'API 'TheMovieDB' via leur endpoint 'discover/movie'.

--> Evidemment il s'agira de remplacer la valeur de 'api_key' par votre clé généré sur le site de 'TheMovieDB'

// Fichier /pages/api/discover.js
export default async function handler(req, res) {
try {
const response = await fetch(
'https://api.themoviedb.org/3/discover/movie?api_key=xxxx'
);
const data = await response.json();

res.status(200).json({ movies: data.results });


} catch (error) {
console.error('Error fetching movies:', error);
res.status(500).json({ error: 'Error fetching movies' });
}
}

--> Vous trouverez également dans ce bout de code un exemple d'un gestion d'erreur try/catch javascript.

Templating React et appels HTTP depuis le Front-End

--> A l'interieur du dossier 'pages', toute l'arborescence qui est en dehors du dossier '/pages/api' est considéré par le
framework Next.JS comme étant des pages Front-End React.

--> Sur le même principe que pour ouvrir un endpoint sur notre API, toute l'arborescence proposée correspondra aux routes
URL pour accéder à vos pages.

--> Ainsi on pourrait, par exemple, créer une page Home via un fichier 'home.tsx' correspondante à l'URL
'http://localhost:3000/home'. Celle-ci ferait un appel HTTP GET à notre API sur le endpoint '/api/discover' et afficherait à l'écran
les titres des films suggérés sous forme d'une liste HTML.

// Fichier /pages/home.tsx

import React, { useEffect, useState } from 'react';

const Home = () => {


const [movies, setMovies] = useState([]);

useEffect(() => {
const fetchMovies = async () => {
try {
const response = await fetch(
'http://localhost:3000/api/discover'
);
const data = await response.json();
setMovies(data.movies);
} catch (error) {
console.error('Error fetching movies:', error);
}
};
fetchMovies();
}, []);

return (
<div>
<h1>Popular Movies</h1>
<ul>
{movies.map(movie => (
<li key={movie.id}>{movie.title}</li>

))}
</ul>
</div>
);
};

export default Home;

Exemple des différentes méthodes d'appels HTTP (GET / POST / PUT / DELETE)

--> Endpoint (côté serveur) '/api/exemple'

// Fichier /pages/api/exemple.js

export default function handler(req, res) {


const { method } = req;

switch (method) {
case 'GET':
// Traitement pour l'appel GET
res.status(200).json({ message: 'GET request' });
break;
case 'POST':
// Traitement pour l'appel POST
const params = req.body;
res.status(200).json({ message: 'POST request' });
break;
case 'PUT':
// Traitement pour l'appel PUT
res.status(200).json({ message: 'PUT request' });
break;
case 'DELETE':
// Traitement pour l'appel DELETE
res.status(200).json({ message: 'DELETE request' });
break;
default:
res.status(405).json({ error: `Method ${method} Not Allowed` });
break;
}
}

--> Template React (côté client) 'http://localhost:3000/exemple'

//Fichier /pages/exemple.tsx

import React, { useEffect, useState } from 'react';

const API_URL = 'https://api.example.com';

const ExampleComponent = () => {


const [data, setData] = useState(null);

// GET request
const fetchData = async () => {
try {
const response = await fetch(`${API_URL}/endpoint`);
const data = await response.json();
setData(data);
} catch (error) {
console.error('Error fetching data:', error);
}
};

// POST request
const postData = async () => {
try {
const response = await fetch(`${API_URL}/endpoint`, {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ name: 'John', age: 30 })
});
const data = await response.json();
console.log('Data posted:', data);
} catch (error) {
console.error('Error posting data:', error);
}
};

// PUT request
const updateData = async () => {
try {
const response = await fetch(`${API_URL}/endpoint`, {
method: 'PUT',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ name: 'Jane', age: 35 })
});
const data = await response.json();
console.log('Data updated:', data);
} catch (error) {
console.error('Error updating data:', error);
}
};

// DELETE request
const deleteData = async () => {
try {
const response = await fetch(`${API_URL}/endpoint`, {
method: 'DELETE'
});
const data = await response.json();
console.log('Data deleted:', data);
} catch (error) {
console.error('Error deleting data:', error);
}
};

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

return (
<div>
<h1>API Examples</h1>
{data ? (
<div>
<h2>Data from API:</h2>
<pre>{JSON.stringify(data, null, 2)}</pre>
</div>
) : (
<p>Loading data...</p>
)}

<button onClick={postData}>POST Data</button>


<button onClick={updateData}>PUT Data</button>
<button onClick={deleteData}>DELETE Data</button>
</div>
);
};

export default ExampleComponent;

Vous aimerez peut-être aussi