-1

I am trying to push a React component into a javascript array. I am expecting the values in that array to be what the React component returns. Instead of that I get an array containing objects of like this: $$typeof: Symbol(react.element)....

Here is my code: loads books from an API when button is clicked and appends then to list of books already displayed (basically infinite scrolling):

Books:

function Books({ page }) {
  const fetcher = url => api.get(url).then(response => response.data);
  const { data: books } = useSWR(
    `/books?page=${page}`,
    fetcher
  );

  return books ? (
    <>
      {books.map(book => (
        <Book key={book.id} book={book} />
      ))}
    </>
  ) : null;
}

IndexPage:

class IndexPage extends React.Component {
  constructor(props) {
    super(props);
    this.state = { pages: 1 };
  }

  load = () => {
    this.setState({ pages: this.state.pages + 1 });
  };

  render() {
    const books = [];
    for (let page = 1; page <= this.state.pages; page++)
      books.push(<Books page={page} key={page} />);    

    console.log(books) // logs `$$typeof: Symbol(react.element)...` instead of `[null]`.

    return (
      <>
        {books.length ? (
          books
        ) : (

          // This never executes because `books.length` is never zero
          <li>No books yet.</li>
        )}

        <button onClick={this.load}>Load More Books</button>
      </>
    );
  }
}

My goal is to find a way to display <li>No books yet.</li> in the code below but I cannot find a way to do it dealing with the values I find in the array. Right now, if there are no objects I just see a blank page.

How can I make sure that the React component actual return values are stored in my array instead of these "symbol" objects?

fredperk
  • 737
  • 1
  • 9
  • 22
  • Those are as actual objects as you're going to get – only when React.js renders the element objects you get HTML. What do you actually want to do here? – AKX Nov 05 '20 at 20:46
  • Figure out a way to display `
  • No books yet.
  • ` when the books array is empty... Nothing more, nothing less... – fredperk Nov 05 '20 at 20:47
  • What fails in your code? Looks fine to me – Dominik Nov 05 '20 at 20:48
  • I updated question. Basically I cannot figure out a way to display message when books array is empty. Right now I just see a blank page. – fredperk Nov 05 '20 at 20:50
  • Well, you are always pushing a `` element into the array so long as `this.state.pages` >= 1. – AKX Nov 05 '20 at 20:50
  • 1
    After all, you can't know whether or not there are books before you've fetched them. Perhaps you should move the fetch/fetch more logic into the `IndexPage` component? – AKX Nov 05 '20 at 20:51
  • I'm confused. Your state starts out with `page:1`, your forloop sets `books` array by `for (let page = 1; page <= this.state.pages; page++)`, so, there will always *be* books, because `1 <= 1` is TRUE, and it will pass one iteration. Yet you're trying to display "No books yet" when it's zero, which is always false. – HoldOffHunger Nov 05 '20 at 20:54
  • True, but when I call Books and there aren't any actual books in my database I am kind of expecting to get back and empty array (or something with 1 null element in it) – fredperk Nov 05 '20 at 20:56
  • Then change your logic to start out with pages: 0, so you'll have zero pages, which, will then display it correctly. – HoldOffHunger Nov 05 '20 at 20:56
  • But I do want to start out with books for when there are some... – fredperk Nov 05 '20 at 20:57
  • Hi, fredperk: Did you finally figure out lifecycles of API-based, react projects? Let me know if my answer helped at all, at least in explaining what's going on. Seems like someone liked my answer, and someone didn't! But I got no explanation, so I have no idea why. – HoldOffHunger Nov 06 '20 at 15:28
  • I worked around it by using a global variable to indicate whether there are more definitions available to be loaded. I might post an answer in the future if I have time – fredperk Nov 06 '20 at 16:06
  • @fredperk: [Global variables are bad.](https://stackoverflow.com/a/485020/2430549) Please don't post that answer. I recommend understanding the documentation before attempting an answer, for instance, like the documentation linked in my answer, thanks. – HoldOffHunger Nov 07 '20 at 14:54