I'm learning Svelte and I want to use data from one JSON API in three components. The data looks like this:
{
"stats": {
"currentYear": {
"total": 6,
"success": 6
},
"thirty": {
"total": 30,
"success": 28
},
"hundred": {
"total": 100,
"success": 92
},
"allTime": {
"total": 789,
"success": 728
}
},
"heatmap": {
...
},
"other": {
...
}
}
I retrieve the data via onMount in the App.svelte main component via async fetch, this works well. Then I want to pass each object to its corresponding component, so the stats object gets passed to Stats.svelte, the heatmap object to Heatmap.svelte etc.
To illustrate my issue, in Stats.svelte I am trying to display percentage values for each time period, for example:
- current year: 100%
- last thirty days: 93%
- last 100 days: 92%
- all time: 92%
Also, the CSS class for each will be based on some threshold values to change the colour (x >= 95: green, 95 > x >= 90: yellow, x < 90: red).
So some basic computation is needed which I wanted to have in a generic function, like shown below.
The stats object does get passed in from the parent component App.svelte, and if all I wanted to do is to show its values in the HTML via the {#await} block, this would work fine. However, I want to do some calculations, so I wanted to call a function that would use the stats object's data, but I do not know how to call this function at the right moment. Calling it on onMount does not work, because it's too early, the data coming in from the parent component has not yet been received.
<script>
import { onMount } from "svelte"
export let stats
let currentYearClass, currentYearStat
const calcPercentage = async (period) => {
currentYearStat = stats[period].currentYearSuccess * 100 / stats[period].currentYearTotal
currentYearClass = 'green'
}
onMount( async () => {
calcPercentage('currentYear')
})
</script>
<div id="stats">
{#await stats}
<div>Waiting for stats ...</div>
{:then stats}
<div class="{currentYearClass}" id="currentYear">{currentYearStat}</div>
...
...
{/await}
</div>