If the statement is just that sometimes it’s appropriate to have callbacks, absolutely. A library that only logs in places where it really needs a callback is poorly designed.

I still don’t want to have to provide a 429 callback just to log, though. The library should log by default if the callback isn’t registered.

It doesn’t have to provide a specific callback. This can be a starting point (Java):

  var client = aClient()
   .onError((request,response) -> { 
      LOG.debug(…); 
      return FAIL; 
   }).build();
And eventually you do this:

   return switch(response.code()) {
      case 429 -> RETRY;
      default -> FAIL;
   }
Or something more interesting, e.g. with more details of retry strategy.