brklyn8900 brklyn8900 -3 years ago 153
Javascript Question

VueJS combine data sources

I have two data sources, one that I created inside my Vue instance and another that I am importing from an api. How do I match the data that I get from the api and combine it with the data I created to display in one table?

HTML:

<div class="ui container" id="app">
<br>
<div class="ui two column divided grid">
<div class="row">
<div class="ten wide column">
<table class="ui unstackable green table">
<thead>
<tr>
<th>Instrument</th>
<th class="right aligned">Position</th>
<th class="right aligned">Price</th>
<th class="right aligned">Total</th>
<th class="right aligned">%</th>
</tr>
</thead>
<tbody>
<tr v-for="item in watchlist">
<td>{{ item.instrument }}</td>
<td class="right aligned">{{ item.position }}</td>
<td class="right aligned"></td>
<td class="right aligned"></td>
<td class="right aligned"></td>
</tr>
</tbody>
</table>
</div>
<div class="six wide column" :attribute="priceData">
<table class="ui unstackable red table">
<thead>
<tr>
<th class="center aligned">Coin</th>
<th class="center aligned">Price</th>
</tr>
</thead>
<tbody>
<tr v-for="coin in prices">
<td>{{ coin.name }}</td>
<td class="center aligned">{{ coin.price_usd }}</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>


Currently I have two tables that each displays the data that I would like to combine into one table.

Vue:

new Vue({
el: '#app',
data: {
watchlist: [
{ instrument: 'Artbyte', position: 10000 },
{ instrument: 'Civic (CVC)', position: 1000 },
{ instrument: 'IOTA', position: 600 },
{ instrument: 'Basic Attention Token', position: 600 },
{ instrument: 'Sentiment (SAN)', position: 500 },
{ instrument: 'TenX', position: 400 },
{ instrument: 'OmiseGo', position: 100 },
{ instrument: 'EOS', position: 200 },
{ instrument: 'Litecoin', position: 30 },
{ instrument: 'Ethereum', position: 10 },
{ instrument: 'Bitcoin', position: 2 },
{ instrument: 'District0x', position: 2000 },
{ instrument: 'Aragon', position: 60 },
{ instrument: 'LBRY Credits', position: 200 }
],
prices: []
},
computed: {
priceData: function () {
var t = this
axios.get('https://api.coinmarketcap.com/v1/ticker/')
.then(function (response) {
t.prices = response.data
})
.catch(function (error) {
console.log(error)
})
},
getPrices: function () {
return this.price
}
}
})


heres a jsfiddle https://jsfiddle.net/brklyn8900/83y53b2k/12/

Answer Source

priceData should not be a computed; it does not return anything. It should run in the created phase.

You can write a computed to combine the two data sources like so:

    created() {
        var t = this
        axios.get('https://api.coinmarketcap.com/v1/ticker/')
          .then(function (response) {
            t.prices = response.data
          })
          .catch(function (error) {
            console.log(error)
          })        
    },
    computed: {
      combinedData() {
          return this.prices.map(c => {
              var obj = Object.assign({}, c);
              var item = this.watchlist.find(w => w.instrument === obj.name);
              if (item) {
                  Object.assign(obj, item);
              }
              return obj;
          });
      }
    },

Updated fiddle

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download