4

What Im looking is simple. As soon as I render my template it will make an API-Call to my Webserver and render the data to the template. Now I want to watch these datas in the vue component for coming changes. Whenever something has changed I want to update the template with the data coming from the API.

One Solution is that I could write something like a refresh method that will be called every 10 seconds. (Tbh. that is sth. that i dont want)

I want a way like Angular with observers.

Btw. Im new to vue and I started learning Vue with Laravel

Edit: My Code:

Vue.component

<template> <div class="w-50"> <table class="table "> <thead> <tr> <th scope="col"></th> <th scope="col"></th> </tr> </thead> <tbody> <tr v-for="user in users" v-bind:key="user.id"> <td>{{ user.name }}</td> <td>{{ user.timer }}</td> </tr> </tbody> </table> </div> </template> <script> export default { data() { return { users: [], user: { id: '', active: '' } }; }, mounted() { axios.get('/users') .then(res => { this.users = res.data; console.log(res.data); }) } } </script> 

I did as you mention below. But the view is not updating if the data changes.

2
  • You could use something like socketio which utilises web sockets. It will feed data down to your site when there is data.# Commented Jan 13, 2019 at 17:09
  • Thats a great idea. I will do some research tonight (Mb laravel provides some helpful utilities out of the box) Commented Jan 14, 2019 at 10:59

5 Answers 5

5

You can use vue-rx to work with Observables in Vue.js.

The following demo makes an AJAX call every 10 seconds to the API service that returns a random joke:

new Vue({ el: '#demo', subscriptions: function () { return { joke: rxjs.timer(0, 10000).pipe( rxjs.operators.switchMap(() => rxjs.ajax.ajax('https://geek-jokes.sameerkumar.website/api')), rxjs.operators.map(res => res.response) ) } } })
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script> <script src="https://unpkg.com/rxjs/bundles/rxjs.umd.js"></script> <script src="https://unpkg.com/[email protected]/dist/vue-rx.js"></script> <div id="demo">{{ joke }}</div>

Sign up to request clarification or add additional context in comments.

Comments

0

I'd take a look at something like Socket.IO. It utilises websocket's so which is a 2 way connection to and from your client to the server. This allows the server to tell your website about changes and feed that data down without you having to poll for it (worth noting, socketio will poll for information is websocket's aren't supported though).

1 Comment

Thanks for you answer. Will do some research tonight.
0

Laravel comes with an out of the box solution for my problem. The key word for this is Broadcast events. With this approach it is really easy to handle socket connections. Adding to this wonderful feature you can use Socket.io and Redis.

Laravel Doc: https://laravel.com/docs/5.7/broadcasting

Since I didnt know that vue always rerenders the template whenever my data has changed, there is no longer need for sth. like a observer in Angular

Comments

0

You didn't include any code, so I'll just add my example:

that is a template tag:

<template> <div> <h1> {{title}} </h1> </div> </template> 

script:

data(){ return { title: '', }, }, mounted(){ axios.get('/api/items/all').then(response => { this.title = response.data.title; }); } 

and that should be enough for Vue.js to pick up changes and render properly a new title (in my example). If you want to watch for changes before they are rendered, you can add a watch property like that:

watch:{ 'title': function (newVal, oldVal) { // you can work with a new value here }, } 

If you need more information on this, you can read Vue docs on Computed Properties and Watchers.

6 Comments

This is correct although I would also like to note that you don’t even need the watcher to have the template render again; setting the reactive data.title will already have the template show the new title. The op’s question is too limited imo; what is the exact problem you’re running into?
Yes, you are right, that’s why I separated the ‘watch’ property from the “main” part of my answer. I just suspect that OP wants something more.
I agree - his question isn’t clear on what he wants to achieve
I only receive the data through an API Call right, the next step is to update my current view whenever the data of my database has changed
If you think about observers like passing message via publish and subcribers
|
0

You are sort-of asking 2 or 3 questions at the same time, so I will try to answer this in parts.

Angular observables in Vue

A direct replacement for Angular observables is the Vue event system. You can listen for events with this.$on and stop listening with this.$off. To do this application wide you need to make something like an event bus:

Vue.prototype.$bus = new Vue(); // in components mounted () { this.$bus.$on('myMessage', this.handleMyMessage); }, beforeDestroy () { this.$bus.$off('myMessage', this.handleMyMessage); } 

That said, it doesn't sound like this is what you actually want to use.

Refreshing data

I suspect that you want to abuse the retry() method to redo the request over and over, but there is honestly no reason to use that. You can just put the request in a method and call it within an interval.

A better method to update your data may be to use a websocket server, but that is something you would need to set up. Without it you either have to do the api requests repeatedly, or don't bother refreshing it until the user wants to.

Updating the template

The data in Vue is always reactive. If the data that is referenced in the template changes, the template automatically rerenders. If you change an object, you may need to use the helper methods Vue.set or Vue.delete (docs). This will ensure the data stays reactive, and thus updates the rendered template.

1 Comment

Thanks for this information. Im trying to do this with websockets. I think thats the best way for my problem. Can you recommend some websites where they show simple solutions ?

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.