This is a followup question to this one (it's not necessary to read that question to answer this one).
Take the following React component as example:
class Greeting extends React.Component {
constructor() {
fetch("https://api.domain.com/getName")
.then((response) => {
return response.text();
})
.then((name) => {
this.setState({
name: name
});
})
.catch(() => {
this.setState({
name: "<unknown>"
});
});
}
render() {
return <h1>Hello, {this.state.name}</h1>;
}
}
Using Jest, here's how we could assert that name
equals to some text returned from the getName
request:
test("greeting name is 'John Doe'", () => {
const fetchPromise = Promise.resolve({
text: () => Promise.resolve("John Doe")
});
global.fetch = () => fetchPromise;
const app = shallow(<Application />);
return fetchPromise.then((response) => response.text()).then(() => {
expect(app.state("name")).toEqual("John Doe");
});
});
But the following doesn't feel right:
return fetchPromise.then((response) => response.text()).then(() => {
expect(app.state("name")).toEqual("John Doe");
});
I mean, I'm somewhat replicating the implementation in the test file.
It doesn't feel right that I have to invoke then()
or catch()
directly in my tests. Especially when response.text()
also returns a promise and I have two chained then()
s just to assert that name
is equal to John Doe
.
I come from Angular where one could just call $rootScope.$digest()
and do the assertion afterwards.
Isn't there a similar way to achieve this? Or is there another approach for this?