1
4

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

オフラインで動作する祝日かどうかを判定してCIをスキップさせるPythonスクリプト

Last updated at Posted at 2018-11-28

ローカルファイルに記載した日付と一致するかどうかを判定して、祝日などにCIをスキップできるシンプルなPythonスクリプトの実装方法と使用方法を記載します。

背景

現在CIで使用しているクラウドサービス上のVMは、稼働時間で課金されるため、休日や祝日などの使用しない日は起動させたくない。しかし、クラウドサービスで設定できるのは、土日などの決まった曜日だけなので、祝日や特定の日付などに起動をスキップできなかった。

内閣府のデータを使用して祝日かどうかを判定できるメンテナンスフリーなツールを公開してくださっている方がすでにいますが、会社独自の休日への対応や、外部のネットワークに依存せずに祝日を判定したかった。

そこで、オフラインで判定できるスクリプトを作成しました。

動作確認環境

  • python 2.6.6, 3.7.1
  • CentOS release 6.8
  • Windows 10 version 1809

実装方法

以下のisholiday.pyholidays.txtを同一ディレクトリに配置します。

isholiday.py
"""
Check whether holiday or not based on holidays.txt.
"""

import sys, os


def get_holidays_list():
    holidays_list = []
    target_path = os.path.join(os.path.dirname(__file__), 'holidays.txt')
    with open(target_path, 'r') as f:
        for row in f:
            holidays_list.append(row.strip())
    return holidays_list

def is_holiday(date):
    if date in get_holidays_list():
        return True
    else:
        return False


if __name__ == '__main__':
    if len(sys.argv) >= 2:
        if is_holiday(sys.argv[1]):
            print("It's a holiday!")
            sys.exit(0)
        else:
            print("It's a business day!")
            sys.exit(1)
    else:
        print('Usage: python isHoliday.py `date --iso-8601`')
        sys.exit(2)
holidays.txt
2018-07-16
2018-09-17
2018-09-24
2018-10-08
2018-11-23
2018-12-24
2018-12-31
2019-01-01
2019-01-02
2019-01-03
2019-01-14
2019-02-11
2019-03-21

使用方法

python isholiday.py <日付>

<日付>はYYYY-MM-DD形式で指定します。

例:

python isholiday.py `date --iso-8601`

実行した日がholidays.txtに含まれている場合は終了コード0を、
含まれていない場合は1を返します。

CIから呼び出す場合:

#!/bin/sh
python /path/to/isholiday.py `date --iso-8601`
if [ "$?" = "0" ]; then
  echo "Skip holiday!" 
  exit 0
fi

新しい祝日を追加する方法

holidays.txtにYYYY-MM-DD形式で追加してください。
不要な行は削除してしまって構いません。

注意: 2018-07-16の行は後述のテストで使っているため、削除してしまうと、テストが失敗します

テストの実行方法

python -m unittest tests.py

tests.py
import unittest
import isholiday

class TestGetHolidaysList(unittest.TestCase):
    def test_file_read(self):
        self.assertTrue(len(isholiday.get_holidays_list()) > 0)

class TestIsHoliday(unittest.TestCase):
    def test_holiday(self):
        self.assertTrue(isholiday.is_holiday('2018-07-16'))
    def test_not_holiday(self):
        self.assertFalse(isholiday.is_holiday('2018-07-17'))

if __name__ == '__main__':
    unittest.main()

問題点

この実装方法では、毎年holidays.txtを更新する必要があります。そのため、部署異動などでメンテナンスする人がいなくなったりすると、CIをスキップできなくなります。(可能な限りシンプルに実装していますので、後任の方への引き継ぎは比較的容易だと思います)

1
4
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
4

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?