Not so fast.
There are a few strange behaviors (really, bugs in my opinion) to learn before attempting to use it, or you can get into pulling-one's-hair-out situation pretty quickly. One basic understanding you need to have (and missing from the documentation) is that for any recurring holiday entered from the UI, there's only one instance/record exists - supposedly for the upcoming one - in the Holiday object if you query it. If that omission has not made things murky enough, here are some others:
- ActivityDate, which supposedly contains the due date for the configured holiday, will always have the current date/creation date when a holiday is first saved. And it remains that way until it's resaved, which will correct it to the due date (but still subject to the next problem). So good luck using it after saving your holiday from the UI.
- ActivityDate also may or may not show a due date that is coming. Ideally, since the object contains single-instance info for holidays, you'd think it always stores the upcoming ones. Not so. If you enter the holiday with a Start Date in the past from the UI, you may end up getting an old instance in the Holiday object, i.e., the ActivityDate contains a past holiday date. For instance, if you create a Labor Day holiday on 10/5/2012, and set the Start Date to be 9/1/2012, you would actually end up 9/3/2012 (after saving it twice) in the ActivityDate. So, to get it to behave helpfully, always make the Start Date to be current or future dates.
- For Yearly holidays, you get an option to set the date this way: "On the nth day of month". You can save it that way too. But the ActivityDate you get doesn't match your rule at all. In fact, only the "On every month day-x" choice is valid. Well, if the other one doesn't work, why leave it enabled for Yearly??