1

I have a Vue 3 website showing a list fetched from a REST-API (using the fetch method). Then sometimes this list is modified in the original DB and I would like to update my vue component accordingly. The good news is that a webhook is posted to me by the DB service when an entry is modified. However, I do not know how to consume this webhook in my Vue project.

I know how to consume it with an express server with something like

app.post("/hook", (req, res) => {
  console.log(req.body)
}

but I don't see how to connect this with my Vue app ?
Maybe it's not even a good approach.

--- Update:

I have implemented @kissu solution (SSE version) but I still have an issue. I have an Express server running : ```js const app = express(); ``` and i wait for a webhook:
app.post("/hook", (req, res) => {
  x=req.body.my_item;
  newUpdate = true;
  res.status(200).end() 
})

and I have a get route for the SSE

app.get('/events', async function(req, res) {
    const headers = {
      'Content-Type': 'text/event-stream',
      'Connection': 'keep-alive',
      'Cache-Control': 'no-cache',
      'Access-Control-Allow-Credentials' : false,
      'Access-Control-Allow-Origin': 'https://grange.vercel.app',
  };
  res.writeHead(200, headers);
    while (true) {    
      await new Promise(resolve => setTimeout(resolve, 500));
      if (newUpdate)
        {
          res.write(`data: ${x}\n\n`);
          res.send(`data: ${x}\n\n`);
          newUpdate = false;
        }
  }
});

and await app.listen(443);

On the Vue side I have

sseClient = this.$sse.create({
     format: 'plain',
     polyfill: true,
     url: 'https://sse.mydomain.fr/events',
     withCredentials: false,
    });

    sseClient.connect()
    .catch((err) => console.error('Failed make initial connection:', err));

    sseClient.on('', this.handleMessage)

and handleMessage do the job of updating my page.

It works for a while then after a minute of inactivity (or sometimes randomly) I receive an 404 error from the sseserver (on the Vue page) because "Access-Control-Allow-Origin is missing". It looks like somehow, my Vue app cannot grab the header of the SSE sometimes and then fail.

Any suggestion @kissu ?

Quentin
  • 13
  • 5
  • Check that one for CORS: https://stackoverflow.com/a/72211930/8816585 – kissu Dec 04 '22 at 15:11
  • Thank you for the link, but It works initially (my CORS initial authorization is ok) and failed after a while. I dont get something in the SSE I imagine, since it looks like I send the header too often. – Quentin Dec 04 '22 at 15:42
  • Probably something linked to Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client – Quentin Dec 04 '22 at 15:42
  • This error is when you do send an answer twice. I guess that `res.write` and `res.send` are the issue here. Or something sent from the backend at least. – kissu Dec 04 '22 at 15:46

1 Answers1

0

A client-side app cannot react to a webhook per se.
You will need some kind of polling or socket communication like:

  • long polling
  • server sent events
  • websockets
kissu
  • 40,416
  • 14
  • 65
  • 133
  • But i could run vue in SSR mode, no ? – Quentin Dec 02 '22 at 20:20
  • @Quentin Vue is an SPA by default. Even if you could statically render it, there is no MPA-SSR behavior like WordPress, no. – kissu Dec 02 '22 at 20:58
  • But @kissu, i understood SSR was possible with Vue (https://vuejs.org/guide/scaling-up/ssr.html). Maybe should i use Nuxt instead ? – Quentin Dec 02 '22 at 21:28
  • @Quentin If you want a truly solid solution regarding SSG/SSR, you could indeed use Nuxt. Deploying a Nuxt3 app as an edge function could be a way of having a fast SSR. Your hydrated client-side app will meanwhile not reload itself. The solutions in my initial answer, a manual hard refresh of the page or a service worker could meanwhile help on that aspect. – kissu Dec 02 '22 at 23:22
  • Hi @kissu. So I ve implemented your solution (SSE version) but I still have an issue. – Quentin Dec 04 '22 at 14:59