I'm not Sandi Metz but there are a few things that captured my attention about that piece of code.
You're using a service/business/whatever object and that is good ™ (instead of pushing all that code down in the model)
I would pass the book (and the author, unless you infer it from the book object) as an argument to publish book, this makes your code easier to test and mock.
def publish_book(book, author)
finalize_book(book) && author.increase_book_count! && send_announcement_email
We're a place where coders share, stay up-to-date and grow their careers.
We strive for transparency and don't collect excess data.