Solution EFM React Js
Exercice IV
Solution EFM React Js
1-installer redux : commandes;
npm install redux
npm install react-redux
2-installer react-router-dom : commande
npm install react-router-dom
3-installer axios : commande
npm install axios
4-Créer Livrereducer.js
Solution EFM React Js
// declaration du state :
const INITIAL_STATE={
livres:[
{id:1,titre:"React js",categorie:'front',couverture:'https://i1.wp.com/leblogducodeur.fr/wp-content/uploads/
2019/12/composants-reactjs.png?fit=339%2C149&ssl=1'},
{id:2,titre:"Laravel ",categorie:'back',couverture:'https://zonetuto.fr/wp-content/uploads/2023/01/framework-
php-laravel-logo-2048x594.png'},
// declaration des actions à executer sur le state
function Livresreducer(state=INITIAL_STATE,action)
// action ADD : Ajouter un nouveau livre
if(action.type==='ADD')
let nlivre={};
nlivre.id=action.payload.id; nlivre.titre=action.payload.titre;
nlivre.categorie=action.payload.categorie; nlivre.couverture=action.payload.couverture;
let nlivres=[...state.livres];
nlivres.push(nlivre);
return {livres:nlivres}
// action DEL : Supprimer un livre
if(action.type==='DEL')
let nlivres=state.livres.filter((livre)=>{
return livre.id!=action.payload.id
})
return {livres:nlivres}
}
Solution EFM React Js
// action UPD : Modifier un livre
if(action.type === 'UPD') {
let id = action.payload.id;
let ntitre = action.payload.titre;
let ncategorie = action.payload.categorie;
let ncouverture = action.payload.couverture;
let nlivres = [...state.livres];
// Trouver l'index du livre dans le tableau "livres"
let index = nlivres.findIndex(livre => livre.id == id);
// Mettre à jour les informations du livre
nlivres[index] = { ...nlivres[index], titre: ntitre, categorie: ncategorie, couverture: ncouverture };
// Retourner le nouveau tableau de livres modifié
return { livres: nlivres };
return state
export default Livresreducer;
Solution EFM React Js
5-Créer store.js
import { createStore } from "redux";
import Livresreducer from "./reducer/Livrereducer";
const store=createStore(Livresreducer)
export default store
6-index.js
import store from './redux/store';
import { Provider } from 'react-redux';
import {BrowserRouter} from 'react-router-dom'
<Provider store={store}>
<BrowserRouter>
<App />
</BrowserRouter>
</Provider>
7-App.js
import {Routes,Route} from 'react-router-dom'
import Addlivre from './components/Addlivre';
import Listlivres from './components/Listlivres';
import Edit from './components/Edit';
import Navbar from './components/Navbar';
import Detail from './components/Detail';
import Api from './components/Api';
function App() {
return (
<div className="App">
<Navbar/>
<Routes>
<Route path="/" element={<Listlivres />} />
<Route path="/ajouter" element={<Addlivre/>} />
<Route path="/Details/:id/:titre/:categorie/:couverture" element={<Detail />} />
<Route path="/Edit/:id/:titre/:categorie/:couverture" element={<Edit />} />
<Route path="/api" element={<Api />} />
<Route path="api/Details/:id/:titre/:categorie/:couverture" element={<Detail />} />
</Routes>
</div>
);
}
export default App;
Solution EFM React Js
8-Listlivres.js
import React from 'react'
import { useDispatch, useSelector } from 'react-redux'
import './List.css'
import {Link} from 'react-router-dom'
export default function Listlivres() {
// recupérer le states livres depuis le Reducer( en utilisant useSelector)
const livres=useSelector(state=> state.livres)
// utiliser le traitement del (en utilisant useDispatch)
const dispatch = useDispatch();
// List.css
const supprimerlivre = (id) => { th,td {
dispatch({ border: 1px solid black;
type: "DEL", padding: 8px;
payload: {id:id} }
}) .c{
}
return ( margin:auto;
<div> }
<h2>Liste des Livres</h2>
<table className='c'>
<tr>
<th>Id</th><th>Titre</th><th>Categorie</th><th>Detail</th><th>Editer</th><th>Supprimer</th>
</tr>
{
livres.map((livre)=>{
return <tr key={livre.id}>
<td> {livre.id}</td>
<td>{livre.titre} </td>
<td>{livre.categorie} </td>
<td> <Link to={`Details/${livre.id}/${livre.titre}/${livre.categorie}/$
{encodeURIComponent(livre.couverture)}`}>Voir Details</Link> </td>
<td> <Link to={`Edit/${livre.id}/${livre.titre}/${livre.categorie}/$
{encodeURIComponent(livre.couverture)}`}>Editer</Link> </td>
<td><input type="button" onClick={()=>supprimerlivre(livre.id)} value='supprimer' /></td>
</tr>
})
</table>
</div>
)
}
Solution EFM React Js
9-Navbar.js
import React from 'react'
import {Link} from 'react-router-dom'
import './Nav.css'
export default function Navbar() {
return (
<div className='nav-top'>
<Link to="/">Accueil</Link>
<Link to="/ajouter">Ajouter Un livre</Link>
<Link to="/api">Get Books from API</Link>
</div>
)
}
10-Nav.css
.nav-top {
margin: 75px auto 50px;
display: flex;
justify-content: center;
align-items: center;
width: 100%;
max-width: 700px;
background: #333;
border-radius: 3px;
padding: 0px 20px;
box-shadow: 0 10px 20px rgba(19, 19, 19, 0.2);
}
.nav-top a {
font-size: 22px;
text-decoration: none;
color: #f1f1f1;
padding: 20px 20px;
}
Solution EFM React Js
11-Addlivre.js
import React, { useState } from 'react'
import { useDispatch, useSelector } from 'react-redux'
export default function Addlivre() {
// declaration des states :
const[id,setId]=useState();
const[titre,setTitre]=useState();
const[categorie,setCategorie]=useState();
const[couverture,setCouverture]=useState();
// utiliser le traitement add (en utilisant useDispatch)
const dispatch = useDispatch();
const ajouterlivre = () => {
dispatch({
type: "ADD",
payload: {id:id,titre:titre,categorie:categorie,couverture:couverture}
})
setId('');
setTitre('');
setCategorie('');
setCouverture('');
}
return (
<div>
<h1>Ajouter un nouveau Livre :</h1>
Id : <input type="text" value={id} onChange={(e)=>setId(e.target.value)} /> <br /><br />
Titre:<input type="text" value={titre} onChange={(e)=>setTitre(e.target.value)} /> <br /><br />
Categorie:<input type="text" value={categorie} onChange={(e)=>setCategorie(e.target.value)} /> <br
/><br />
Couverture:<input type="text" value={couverture} onChange={(e)=>setCouverture(e.target.value)} /> <br
/><br />
<input type="button" value='Ajouter' onClick={ajouterlivre} />
</div>
)
}
Solution EFM React Js
12-Detail.js
import React from 'react'
import { useParams } from 'react-router-dom';
export default function Detail() {
const {id,titre,categorie,couverture}=useParams();
return (
<div>
<h2>Details du livre :{id}</h2>
<h3>Titre:{titre} </h3>
<h3>Categorie:{categorie}</h3>
<img src={couverture} width={400} height={250} alt="" />
</div>
)
}
Solution EFM React Js
13-Edit.js
import React, { useState } from 'react'
import { useParams } from 'react-router-dom';
import { useDispatch, useSelector } from 'react-redux'
export default function Edit() {
// declaration des states
const {id,titre,categorie,couverture}=useParams();
const [ide,setIde]=useState(id);
const [titree,setTitree]=useState(titre);
const [categoriee,setCategoriee]=useState(categorie);
const [couverturee,setCouverturee]=useState(couverture);
// utiliser le traitement UPD (en utilisant useDispatch)
const dispatch = useDispatch();
const modifierlivre = () => {
dispatch({
type: "UPD",
payload: {id:id,titre:titree,categorie:categoriee,couverture:couverturee}
})
return (
<div>
<h2>Editer le livre id :{id}</h2>
Titre : <input type="text" value={titree} onChange={(e)=>setTitree(e.target.value)}/>
<br /><br />
Categorie : <input type="text" value={categoriee}
onChange={(e)=>setCategoriee(e.target.value)}/> <br /><br />
Couverture : <input type="text" value={couverturee}
onChange={(e)=>setCouverturee(e.target.value)}/> <br /><br />
<input type="button" onClick={modifierlivre} value="Modifier" />
</div>
)
}
Solution EFM React Js
14-Api.js
import React, { useEffect, useState } from 'react'
import { useParams } from 'react-router-dom'; [ // PostMan
import {Link} from 'react-router-dom' {
import axios from 'axios'; "id": 1,
import './List.css' "titre": "Java",
export default function Api() { "categorie": "Mobile",
// declaration du state : "couverture": "https://
const [livres, setLivres] = useState([]);
www.sitedetout.com/wp-content/uploads/
2016/07/java.jpg",
// appel api fetch (useEffect)
/* useEffect(() => { "created_at": null,
fetch('http://127.0.0.1:8000/api/livres') "updated_at": null
.then(response => response.json()) },
.then(data => setLivres(data)); {
}, []);*/ "id": 2,
"titre": "Php",
"categorie": "Dev Web",
// appel api axios (useEffect)
"couverture": "https://
// npm install axios www.imagine-developpement.net/
photos_site/1563788315php-PNG3.png",
useEffect(() => { "created_at": null,
axios.get('http://127.0.0.1:8000/api/livres') "updated_at": null
.then(response => setLivres(response.data)); }
}, []); ]
return (
<div>
<h1>Call Laravel Api :</h1>
<table className='c'>
<tr>
// Laravel Conroller
<th>Id</th>
class LivreController extends Controller
<th>Titre</th>
{
<th>Categorie</th>
/**
<th>Detail</th>
* Display a listing of the resource.
*
</tr> * @return \Illuminate\Http\Response
*/
{ public function index()
livres.map((livre)=>{ {
return <tr key={livre.id}> $livres=Livre::all();
<td> {livre.id}</td> return response()->json($livres);
<td>{livre.titre} </td> }
<td>{livre.categorie} </td>
}
<td> <Link to={`Details/${livre.id}/${livre.titre}/${livre.categorie}/$
{encodeURIComponent(livre.couverture)}`}>Voir Details</Link> </td>
</tr>
})
}
</table>
</div>
)
}