Why does CSS animation through javascript only happen once

Solution 1:

You need to remove the animation, then set it back to reset it:

let navChildren = [...document.getElementById('nav-container').children]

navChildren.forEach(x => {
  x.addEventListener('click', () => {

  })
  x.addEventListener('mouseout', () => {
    x.style.animation = "none";
    setTimeout(function() {
      x.style.animation = 'hoverOut 1s forwards'
    }, 0)
  })
})
ul {
  list-style-type: none;
  margin: 0;
  padding: 0;
  overflow: hidden;
  background-color: #333;
}

li {
  float: left;
}

li a {
  display: block;
  color: white;
  text-align: center;
  padding: 14px 16px;
  text-decoration: none;
}

li a:hover {
  animation: hoverIn 0.5s forwards;
}

@keyframes hoverIn {
  0% {
    background-color: #333;
  }
  100% {
    background-color: #111;
  }
}

@keyframes hoverOut {
  0% {
    background-color: white;
  }
  100% {
    background-color: #333;
  }
}

.active {
  background-color: #222;
}
<html>

<body>
  <ul id='nav-container'>
    <li><a href="#home">Home</a></li>
    <li><a href="#news">News</a></li>
    <li><a href="#contact">Contact</a></li>
    <li><a href="#about">About</a></li>
  </ul>
</body>

</html>

Although an easier way is just to use CSS transitions, no JavaScript required:

ul {
  list-style-type: none;
  margin: 0;
  padding: 0;
  overflow: hidden;
  background-color: #333;
}

li {
  float: left;
}

li a {
  display: block;
  color: white;
  text-align: center;
  padding: 14px 16px;
  text-decoration: none;
  transition: 0.5s;
}

li a:hover {
  background-color: white;
}

@keyframes hoverOut {
  0% {
    background-color: white;
  }
  100% {
    background-color: #333;
  }
}

.active {
  background-color: #222;
}
<html>

<body>
  <ul id='nav-container'>
    <li><a href="#home">Home</a></li>
    <li><a href="#news">News</a></li>
    <li><a href="#contact">Contact</a></li>
    <li><a href="#about">About</a></li>
  </ul>
</body>

</html>

Solution 2:

Add the animationend event listener to refresh the animation.

https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Animations/Using_CSS_animations#using_animation_events

let navChildren = [...document.getElementById('nav-container').children]

navChildren.forEach(x => {
  
    x.addEventListener("animationend",()=>x.style.animation = "none");

    x.addEventListener('mouseout',()=>x.style.animation = 'hoverOut 1s forwards');
})
ul {
  list-style-type: none;
  margin: 0;
  padding: 0;
  overflow: hidden;
  background-color: #333;
}

li {
  float: left;
}

li a {
  display: block;
  color: white;
  text-align: center;
  padding: 14px 16px;
  text-decoration: none;
}

li a:hover {
  animation: hoverIn 0.5s forwards;
}

@keyframes hoverIn {
    0% { background-color: #333; }
    100% { background-color: #111; }
}

@keyframes hoverOut {
    0% { background-color: #111; }
    100% { background-color: #333; }
}

.active { background-color: #222; }
<html>
    <body>
        <ul id = 'nav-container'>
          <li><a href="#home">Home</a></li>
          <li><a href="#news">News</a></li>
          <li><a href="#contact">Contact</a></li>
          <li><a href="#about">About</a></li>
        </ul>
    </body>
</html>