Cannot reference properties of object stored in a signal after being fetched from API

I fetch some data via a REST API and store it in a signal within the onMount hook. The signal stores an array of the fetched data. I can reference all top level members of that array, but when I try to reference their properties I get an error. This only happens for me when I fetch the data from an API. When I pass in the static data via prop or just initialize the signal with the data, it doesn't happen. A reproduction of the problem is below (and also here: https://playground.solidjs.com/anonymous/cd6419ab-38e5-43c8-846e-44dcc9233896) I think there is something fundamental I am missing.
import { render } from "solid-js/web";
import { createSignal, onMount, createEffect } from "solid-js";

function Test() {
const [users, setUsers] = createSignal([]);
const [users2, setUsers2] = createSignal([
{
id: 1
},
{
id: 2
}
])

createEffect(() => {
console.log(users()[0].id) //THROWS ERROR
})

createEffect(() => {
console.log(users2()[0].id) //DOES NOT THROW ERROR
})

onMount(() => {
fetch("https://64062563eed195a99f972501.mockapi.io/users")
.then(res => res.json())
.then(data => {
setUsers(data)
})
})

return (
<></>
);
}

render(() => <Test />, document.getElementById("app")!);
import { render } from "solid-js/web";
import { createSignal, onMount, createEffect } from "solid-js";

function Test() {
const [users, setUsers] = createSignal([]);
const [users2, setUsers2] = createSignal([
{
id: 1
},
{
id: 2
}
])

createEffect(() => {
console.log(users()[0].id) //THROWS ERROR
})

createEffect(() => {
console.log(users2()[0].id) //DOES NOT THROW ERROR
})

onMount(() => {
fetch("https://64062563eed195a99f972501.mockapi.io/users")
.then(res => res.json())
.then(data => {
setUsers(data)
})
})

return (
<></>
);
}

render(() => <Test />, document.getElementById("app")!);
2 Replies
REEEEE
REEEEE2y ago
it's because the data can not be available yet
createEffect(() => {
console.log(users()[0]?.id)
})
createEffect(() => {
console.log(users()[0]?.id)
})
This will work or
createEffect(() => {
if(users().length === 0) return;

console.log(users()[0].id)
})
createEffect(() => {
if(users().length === 0) return;

console.log(users()[0].id)
})
the type error with accessing id is because the users elements don't have a type that includes the id property
eponymous
eponymous2y ago
@._rb Thanks! I wrongly thought that signals took care of that logic for you.
Want results from more Discord servers?
Add your server