Help us understand the problem. What is going on with this article?

祝日をWebAPIから取得するシェルスクリプト

More than 1 year has passed since last update.

平日・休日ログを自動的に仕分けしたい

ある仕事で、土日祝日のログを自動的に休日扱いしたいという要望があった。

土日だったらすぐにわかるけど、祝日ってどうすりゃいいのよ。
月日固定の日付や振替休日はいいとして、春分の日と秋分の日は調べようがないでしょ。
(註:春分と秋分は、毎年天文観測によって二年後の月日が決められます)

休日設定ファイルでも作って毎年打ち込んでもらうしか……、と思っていたら Google先生が囁いた。

Google Calendar APIを使いなさい。

Google先生への質問状

というわけで、さらに詳しくGoogle先生に聞きつつ、ささーっと作ったのが下のシェルスクリプト。

holidays.sh
#! /bin/sh

# このURLは
# Googleカレンダーの「カレンダー設定」→「日本の祝日」→「ICAL」から取得可能
# (2017/01/12現在)
url='https://calendar.google.com/calendar/ical/ja.japanese%23holiday%40group.v.calendar.google.com/public/basic.ics'

curl -s "$url"                           |
sed -n '/^BEGIN:VEVENT/,/^END:VEVENT/p'  |
awk '/^BEGIN:VEVENT/{                    # iCalendar(RFC 5545)形式から
       rec++;                            # 日付と名称だけ抽出
     }                                   #
     match($0,/^DTSTART.*DATE:/){        # DTSTART行は日付であるから
       print rec,1,substr($0,RLENGTH+1); # 「レコード番号 "1" 日付」に
     }                                   #
     match($0,/^SUMMARY:/){              # SUMMARY行は名称であるから
       s=substr($0,RLENGTH+1);           # 「レコード番号 "2" 名称」に
       gsub(/ /,"_",s);                  #
       print rec,2,s;                    #
     }'                                  |
sort -k1n,1 -k2n,2                       | # レコード番号>列種別 にソート
awk '$2==1{printf("%d ",$3);}            # # 1レコード1行にする
     $2==2{print $3;       }             #
     '                                   |
sort                                     # 日付順にソートして出力

ソースコードの中にもメモしているが、祝日一覧を返してくるWebAPIのURLは次のように辿れば見つけることができる。(2014/11/29現在)

  1. ログインしてGoogleカレンダーを開く(ただし最終的に得られたURL自体はログインせず利用可能)
  2. (歯車マークアイコンの中の)「設定」メニュー
  3. 画面上部に「全般」「カレンダー」とある「カレンダー」タブ
  4. 「日本の祝日」リンク
  5. 「カレンダーのアドレス」行にある"ICAL"アイコン

また、例えGoogleがiCalendar形式の配信やカレンダーサービスを止めたとしても、iCalendarはRFCで標準化された規格なので、どこかしらがやっているはず。(Google先生に聞いてみよう)

実行してみる

実行例
$ holidays.sh
20130101 元日
20130114 成人の日
20130211 建国記念の日
20130320 春分の日
20130429 昭和の日
20130503 憲法記念日
20130504 みどりの日
20130505 こどもの日
20130506 こどもの日_振替休日
20130715 海の日
20130916 敬老の日
20130923 秋分の日
20131014 体育の日
20131103 文化の日
20131104 文化の日_振替休日
20131123 勤労感謝の日
20131223 天皇誕生日
20140101 元日
20140113 成人の日
20140211 建国記念の日
20140321 春分の日
20140429 昭和の日
20140503 憲法記念日
20140504 みどりの日
20140505 こどもの日
20140506 みどりの日_振替休日
20140721 海の日
20140915 敬老の日
20140923 秋分の日
20141013 体育の日
20141103 文化の日
20141123 勤労感謝の日
20141124 勤労感謝の日_振替休日
20141223 天皇誕生日
20150101 元日
20150112 成人の日
20150211 建国記念の日
20150321 春分の日
20150429 昭和の日
20150503 憲法記念日
20150504 みどりの日
20150505 こどもの日
20150506 憲法記念日_振替休日
20150720 海の日
20150921 敬老の日
20150922 国民の休日
20150923 秋分の日
20151012 体育の日
20151103 文化の日
20151123 勤労感謝の日
20151223 天皇誕生日
$ 

Google先生は、当年とその前後1年の祝日一覧を教えてくれる。ご覧のとおり、振替休日が発生する場合は元の日付に加えて振替日も示してくれる。日付だけが欲しくて名称が邪魔な場合は最後のsortコマンドの後に、| awk {print $1}などを付け足せばよいので簡単だ。

ちなみに以前は「クリスマスも祝日だ」とGoogle先生はお答えになっていたが、それはなくなったようだ。

Why do not you register as a user and use Qiita more conveniently?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away