Bonjour, j'ai fait une API en Symfony voici le code
//APIController.php

[Route('/API', name: 'app_API')]
public function index(Request $req, EntityManagerInterface $em, ResSlots $resSlots): JsonResponse
{
    $body = $req->getContent();

        //dd($req->query->get('nbcutelry'));
        //dd($req->query->get('date'));
    $slots= $resSlots->getAvailableTimeSlots($em,Carbon::createFromFormat('Y-m-d H:i:s',$req->query->get('date')), intval($req->query->get('nbcutelry'))); //Carbon::createFromFormat('Y-m-d',$req->query->get('date'))

    return new JsonResponse([
        'slots' => $slots,
    ]);
}

}

je fais appel à la route (déclaré dans le .env) dans le app.js (webpack encore) :

setInterval(function () {
// executer tous les x seconds
let date = document.querySelector('calendar').value;
let nbcutlery = document.querySelector('nbcutelry').value;

console.log(process.env.APIRES);
fetch(process.env.APIRES + new URLSearchParams({ date:date, nbcutlery:nbcutlery,})).then(response => {
// traitement de la réponse

},2000)
})

voici le twig de reservation (rendu de la route /res du controlleur indexController) :
{% extends 'base.html.twig' %}

{% block title %}Hello IndexController!{% endblock %}

{% block body %}
{# <p>{% for day,hours in openhours %}
<h3>{{ day }}</h3>
{% if hours != '' %}
{{ hours }}
{% else %}
fermé
{% endif %}
{% endfor %} </p>#}
{{ dump(resslots) }}
<form method="post" action="#"><input id="nbcutelry" name="nbcutelry" type="number" onkeyup="setInterval(this.value)"><input id="date" name="date" type="date">{% for resslot in resslots %}

        <button type="submit">{{ resslot }}</button>
    {% endfor %}</form>

{% endblock %}
{% block javascripts %}

{% endblock %}

Avez vous une idée de comment faire pour qu'il y ait un rafraichissement automatique ?

7 réponses


Ptuner
Auteur

MAJ :
j'ai crée ce code :
let date = document.querySelector('#date');
let nbcutlery = document.querySelector('#nbcutelry');
let slots = document.querySelector('#slot');

let datevalue = null;
let nbcutleryvalue = null;
date.addEventListener('change', (e) =>{
const selectedDate = new Date(e.currentTarget.value);

const year = selectedDate.getFullYear();
const month = String(selectedDate.getMonth() + 1).padStart(2, '0');
const day = String(selectedDate.getDate()).padStart(2, '0');
const hours = String(selectedDate.getHours()).padStart(2, '0');
const minutes = String(selectedDate.getMinutes()).padStart(2, '0');
const seconds = String(selectedDate.getSeconds()).padStart(2, '0');

datevalue = `${year}-${month}-${day} %20 ${hours}:${minutes}:${seconds}`;
console.log(datevalue);
//console.log(datevalue);

});
//datevalue = datevalue.format("yyyy/mm/dd h:i:s");
console.log(datevalue);
nbcutlery.addEventListener('change', (e) =>{
nbcutleryvalue = e.currentTarget.value;
//console.log(datevalue);
});

//console.log();
setInterval(function () {
// executer tous les x secondes

//console.log(process.env.APIRES);
if(datevalue && nbcutleryvalue){
    //const encodedDateValue = encodeURIComponent(datevalue);
    //console.log(encodedDateValue);
    fetch(`http://127.0.0.1:8000/API?nbcutlery=${nbcutleryvalue}&date=${datevalue}`, {
        method: 'GET',
        headers: {
            "Accept": "application/json",
        },
    })
        .then(response => {
            // traitement de la réponse
            return response.json();
        })
        .then(data => {
            // Effacer les éléments existants
            slots.remove();

            // Recréer les éléments à partir des données obtenues
            data.slots.forEach(slotTime => {
                const button = document.createElement('button');
                button.setAttribute('id', 'slot');
                button.setAttribute('type', 'submit');
                button.textContent = slotTime;
                slots.appendChild(button);
            });
        })
        .catch(error => {
            // Gérer les erreurs
            console.log("Une erreur s'est produite :", error);
        });

}

},6000)

console.log(document.querySelector('#date').value);
Voici le résultat :
avant l'appel API
https://ibb.co/8b92Sj0
Après :
https://ibb.co/VQ1jqdc
Données JSON de l'API
https://ibb.co/2FBVv4G
Le Dom n'est pas effacé et le rafraichissement ce produit l'un à coté de l'autre ou par dessus. D'où ça peut venir ?

Ptuner
Auteur

Sachant qu'il y a une erreur dans les créneaux en plus 12:00 disparait et 12h30 et 13h00 ne sont pas supprimées.
Copiez le code d'un ide ou notepad++ on ne peut pas mettre de balise code en réponse je crois...

Bonjour,
Un api n'est pas censé faire un raffraichissement automatique. Tu peux lire une donnée. En enregistré, modifié ou supprimé et ça s'arrête là.
J'imagine que tu souhaites faire un raffraichissement dans ton javascript ? Mais je vois une route "GET", qui ne sert que à lire. Je ne comprend pas vraiment le besoin personnellement.
Si tu souhaites un raffraichissement, tu devrais soit :

  • Recharger toutes les données.
  • Soit tu remplaces l'élement que tu as enregistré dans ton api également sur t'as page à la suite du fetch. Comme ça l'utilisateur n'y verra rien.
Ptuner
Auteur

En fait je fait le fetch pour rafraichir la page (les créneaux) à partir du javascript (la route API est écrite en php en Symfony) ce que j'aimerai faire c'est de rafraichir en temps réel els créneaux disponibles (en fonction du temps et du nombre de couverts ainsi que de l'horaire une méthode d'un service que j'ai crée répond déjà en grande partie à cette problèmatique). On m'a déconseillé d'utiliser Mercure comme je suis débutant.

Le fetch ne sert pas à rafraichir la page. Ce n'est même pas du tout ce qu'il y a dans ton javascript. Dans tous les cas en javascript ce n'est pas possible. Tu pourrai utiliser du React ?
Là en j avascript tu peux simuler une modification. Exemple. Je fais un appel vers mon api pour mo difier le titre. Je le modifie également brutalement en javascript.

Ptuner
Auteur

Donc je ne peux pas rafraichir un morceau de page (ou en AJAX) en utilisant Symfony ?
Non dans l'absolu j'ai commencé un faire ce projet en PHP (Symfony) ils demandent une page dynamique pour réserver des créneaux des clients (pour un repas au restaurant) l'user ne doit pas faire F5 pour voir les nouveaux créneaux (qui ne sont pas pris ou passés). Ceci est pour une évaluation.Je veux m'orienter sur le backend de mon coté aussi d'où l'utilisation du Framework Symfony. Je ne rafraichis pas la page mais supprime les anciens créneaux et en mets de nouveaux à partir de l'API. React c'est du JS d'après mes souvenirs?

Oui, si tu peux utiliser du React, c'est top et plutôt facile à apprendre. Après c'est possible de faire ça en Javascript aussi.
Le principe reste le même.

Tu fais un appel pour récupérer t'es données,
Tu affiches t'as page.
L'utilisateur modifie un élément, tu fais un Update dans ton API.
Tu modifies la valeur sur ta page.