Can anyone help me resolve this Uncaught TypeError when trying to convert an object. This would be really helpful. I'm not sure where the problem is as I'm running out of variables to watch for in the debugger and variables to console.log. Any help would be appreciated.
As suggested, I've edited this problem to show the code and not pictures of the code.
Parent Component
import React, { Component } from "react";
import CatHeading from "./CatHeading";
import CatImage from "./CatImage";
import CatInfo from "./CatInfo";
import config from "../../config";
export default class Cat extends Component {
// initialize state to hold fetch data for cats
constructor(props) {
super(props);
this.state = {
cats: [],
};
this.handleClick = this.handleClick.bind(this);
}
componentDidMount() {
/* when the component is mounted, immediately preform a GET
request to /api/cats
to receive cat image and cat info */
const requestOptions = {
method: "GET",
redirect: "follow",
};
fetch(`${config.REACT_APP_PORT_URL}/api/cats`, requestOptions)
// use chained promises to receive the data from the server
.then((response) => response.json())
.then((responseJSON) => this.setState({ cats: responseJSON }))
.catch((error) => console.log("error", error));
// use this.setState to update state with response data
}
handleClick() {
console.log("button clicked!");
}
// add a timeout method that adopts a dog every 5 seconds
/* add a conditional rendering that will disable the adopt button
if it is not the users turn in the queue*/
render() {
const { cats } = this.state;
// console.log(cats);
/* figure out how to access these props for the children
components*/
return (
<div className="col-md text-center">
<CatHeading cats={cats} />
<CatImage cats={cats} />
<CatInfo cats={cats} />
<div className="mb-5">
{/* add event handler to button to trigger DELETE /api/cats
dequeue a cat, this also will update the state*/}
<button
type="button"
className="btn adopt-button"
onClick={this.handleClick}
>
Adopt!
</button>
</div>
</div>
);
}
}
// add prop types for the props that are passed down
Child Component
import React, { Component } from "react";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { faCaretLeft, faCaretRight } from "@fortawesome/free-solid-svg-icons";
export default class CatImage extends Component {
render() {
console.log(this.props.cats);
const { cats } = this.pops;
console.log(cats[0]);
console.log(Object.keys(cats[0]));
return (
<div className="container">
<div className="row">
<div className="col-2 my-auto">
<button type="button" className="btn btn-primary btn-sm caret">
<FontAwesomeIcon icon={faCaretLeft} className="caret-left" />
</button>
</div>
<div className="col-8">
<img
src="https://images.unsplash.com/photo-1598463166261-357c23778812?ixid=MXwxMjA3fDB8MHxwaG90by1wYWdlfHx8fGVufDB8fHw%3D&ixlib=rb-1.2.1&auto=format&fit=crop&w=1410&q=80"
alt="A smiling golden-brown golden retriever listening to music"
/>
</div>
<div className="col-2 my-auto">
<button type="button" className="btn btn-primary btn-sm caret">
<FontAwesomeIcon icon={faCaretRight} className="caret-right" />
</button>
</div>
</div>
</div>
);
}
}
Console Logged Object with no null or undefined values Console.log(cats[0]) gives me an output of with an object of no undefined or null values. However, using Object.keys(cats[0]) produces an Uncaught TypeError: cannot convert null or undefined to object, even though the object that is logged to the console does not have any null or undefined values as far as I can tell.
Alright, so first let's run through what is happening here and then, later, we'll look at how you can mitigate such issues.
Within the Parent component:
export default class Cat extends Component {
// initialize state to hold fetch data for cats
constructor(props) {
super(props);
this.state = { cats: [] }; // Initially, "cats" is an empty array
}
// other...
}
Therefore when you do this:
console.log()
.console.log(cats[0]);
// > undefined
Object.keys()
non-object argument will be coerced to an object.Object.keys()
finds no property names
[in this case the index
for the array] therefore "undefined" and thus it returns the TypeError.console.log(Object.keys(cats[0]));
// > Uncaught TypeError: Cannot convert undefined or null to object
Solution:
props
while knowing the effect of the React component lifescycle methods.Otherwise, the quickest thing to do would be to add extra check prior to what you want:
// First, we make sure that "cats" is defined
// Second, we ensure that "cats" is not empty
cats && cats[0] && console.log(cats[0]);
// Same for the other
cats && cats[0] && console.log(Object.keys(cats[0]));
If "cats", console.log()
will simply not run.