Github」タグアーカイブ

話題のオープン職務経歴書を書いてみる

概要

以下の記事に一通り目を通して強く影響を受けたので、自分なりに解釈、アレンジしながら書いてみた。

名称について

参考記事では「職務経歴書OSS化」というワードが使われているが、Githubで公開してるだけでOSS要素はあまり無いと思った。本記事ではリクナビの「オープンエントリーシート」に準えて、「オープン職務経歴書」といワードを用いることにする。

といっても、後述のデメリットから職務経歴書というよりはスキルシートに近いので、「オープンスキルシート」とするのが正確かもしれないが、そうすると元の参考記事からさらに離れてしまうので、職務経歴書のワードはそのまま使うことにした。

オープン職務経歴書の概要

名の通り、グローバルに公開した職務経歴書。元記事に倣って、Githubに公開することを想定する。

職務経歴書と言えば転職活動時に使う前提のものとなるが、書き方によっては転職の意思がなくても多くのメリットが得られる。自分で書いてみた感触と、元記事で紹介されている情報をあわせて、メリット/デメリットを整理すると以下の通りになる。

メリット

  • 継続して書いておくと、いざ転職活動などで必要になった際に困らない
  • 自身の経験/スキルを客観視することができる
  • 他人に自身の経験/スキルを説明しやすくなる
  • 他人に自身の職務経歴書を校正してもらえる
  • 話のタネになる。技術アピールのきっかけになる
  • お金がかからない
  • Githubを使えばMarkdownでサクッと書いてサクッと公開できる

デメリット

  • 公開できる情報に制限がある
    — 個人情報
    — 企業情報
    — 各種製品名
  • 記載内容やフォーマットに統一性がない

オープン職務経歴書の例

職務経歴書(履歴書)を英語でCurriculum-Vitaeというらしく、Githubでこのワードを検索すると、リポジトリが山ほど出てくる。
Github Curriculm-Vitae

もちろん、本記事の内容に関係ないリポジトリも数多くあるが、適当にリポジトリを選択してみると、日本人/外国人問わず、多くの職務経歴書(履歴書)が確認できる。また、本記事ではMarkdownを想定しているが、HTMLやPDF、Texなど、様々なフォーマットでも公開されている。

記載内容

既存のオープン職務経歴書をいくつか見てみると、やはり人によって記載している内容は大きく異なる。登壇歴や出版歴など、輝かしい功績を記載している人もいれば、具体的な会社名や製品名を出した、本物の職務経歴書のような人もいる。

本記事では、私がグローバルに公開しても確実に問題ないと思った範囲についてのみ記載することにする。そのため、具体的な会社名、製品名は伏せ、どのような技術を用いた業務を行ってきたかを確認できるようにする。

公開できる範囲で、精一杯のアピールができるように、今回は以下のような構成にした。

基本情報

氏名、メールアドレス、各種SNSアカウントなど、公開できる範囲で記載。私は割りと本名をネット上で利用しているのでここは気にしなかった。流石に電話番号や住所は書かない。

資格

死角?ありません、無敵です。
とりあえずIPA資格だけ、名前と取得年月を記載。運転免許とか簿記とか、エンジニアに本質的に関わらないものは割愛。

自然言語

日本語/英語どのぐらいいけるか。あえて正直に書いた。

プログラミング言語/フレームワーク

趣味、実務問わず、一定期間以上使っていた言語及びフレームワークを列挙。それぞれの言語について、実務の経験年数と備考を記述。

実務経歴

これまで実務で関わってきたプロジェクトを、特定されないような大雑把な表現で紹介。個々のプロジェクトについて、期間及び使用技術、担当業務などを記載。

成果物

以上を元に、以下のオープン職務経歴書を作成した。
Sa2knight/Curriculum-Vitae

所感

  • 転職うんぬんでなく、経歴を客観視しつつ常に更新し続けることが醍醐味だと感じた
  • 「君、何が出来るの?」的な問に対して今後はURLを張るだけで解決しそう
  • そもそもエンジニアがこういった情報を紙で出すことが前時代的なのでは
  • Githubに置いてるので、そのままその人のソースコードを閲覧できるのはエンジニア的には大きいかも
  • 経験年数で技量を測るのはナンセンスだと思うけど現状コレが主流なので仕方ない
  • Markdownだとテーブルのスタイリング調整ができないのでちょっと辛い

[Python3] GithubAPI/TwitterAPIを用いて、最新のコミットログをツイートする

前提

以下の環境で実装、動作確認

要素 バージョン
debian 8.6
python 3.6.2

概要

GithubAPIを用いて、自身がGithub上のリモートリポジトリに対してpushした内容からコミットログを取得し、それに関する情報をTwitterAPIを用いてツイートしたお話。

本記事ではTwitterAPIを利用するためのコンシューマキー、アクセストークンは取得済みであることを前提としている。

同じことはGithubのWebhookを使ってできるしむしろ自然だが、その場合サーバーを用意する必要があるので、今回はあえてpull型で非効率なやり方を採用

動作イメージ

リモートリポジトリがGithub上にあるリポジトリに対して適当にコミット/プッシュ

$ git commit -m "コミットテスト"
[master e6bb9e4] コミットテスト
 1 file changed, 1 insertion(+)
$ git push origin master
Counting objects: 3, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (3/3), done.

今回実装したコマンドを実行する

$ python main.py

以下のように、リポジトリ名、コミットメッセージ、diffへのリンクがツイートされる

GithubAPIについて

GithubAPIは、名前の通りGithubの各種読み書きを行うためのAPI。
公開されているデータの取得に関しては認証無しで手軽に利用できる。

例えば、curlコマンドを用いて以下のURLに対してGETリクエストを送信すると

curl -i https://api.github.com/users/sa2knight/events

以下のように、該当ユーザのGithubでのイベントログを取得することができる

[
  {
    "id": "6516862394",
    "type": "PushEvent",
    "actor": {
      "id": 16274215,
      "login": "Sa2Knight",
      "display_login": "Sa2Knight",
      "gravatar_id": "",
      "url": "https://api.github.com/users/Sa2Knight",
      "avatar_url": "https://avatars.githubusercontent.com/u/16274215?"
    },
    "repo": {
      "id": 96615971,
      "name": "Sa2Knight/degulog2",
      "url": "https://api.github.com/repos/Sa2Knight/degulog2"
    },
    "payload": {
      "push_id": 1946817475,
      "size": 1,
      "distinct_size": 1,
      "ref": "refs/heads/master",
      "head": "4208370eb0cda0a1bab02fd3fbe5bf7e3e6f5f29",
      "before": "afd8b8647c2b810ceb731a74bad20c7388c19974",
      "commits": [
        {
          "sha": "4208370eb0cda0a1bab02fd3fbe5bf7e3e6f5f29",
          "author": {
            "email": "shingo.sasaki.0529@gmail.com",
            "name": "shingo sasaki"
          },
          "message": "バックアップ追加",
          "distinct": true,
          "url": "https://api.github.com/repos/Sa2Knight/degulog2/commits/4208370eb0cda0a1bab02fd3fbe5bf7e3e6f5f29"
        }
      ]
    },
    "public": true,
    "created_at": "2017-08-27T15:22:08Z"
  },
  {
    "id": "6516846556",
    "type": "PushEvent",
(以下省略)

ここで取得できるイベントは、Webで言う以下のような、そのユーザのリポジトリに対する操作全般の情報なので、今回はこのAPIを用いることにする

ライブラリの導入

今回はPython3を用いて実装するので、Pythonのパッケージ管理ツールであるpipを用いて、以下の二種類のライブラリを導入する。

  • requests
    — HTTPライブラリ
  • twitter
    — TwitterAPI用

TwitterAPIの利用には認証も絡んでくるので、専用のライブラリを利用する。GithubAPIは特定URLにGETするだけなのでHTTPライブラリで直接実行することに。

$ pip install requests
$ pip install twitter

ソースコード

最新版はこちら

import twitter
import requests
import json
import os

FILE_NAME      = "last_id"
EVENTS_URL     = "https://api.github.com/users/sa2knight/events"
REPOSITORY_URL = "https://api.github.com/repos"

def tweet(text):
  auth = twitter.OAuth(consumer_key=os.environ['TWITTER_CONSUMER_KEY'],
                       consumer_secret=os.environ['TWITTER_CONSUMER_SECRET'],
                       token=os.environ['TWITTER_ACCESS_TOKEN'],
                       token_secret=os.environ['TWITTER_ACCESS_SECRET'])
  t = twitter.Twitter(auth=auth)
  t.statuses.update(status=text)

def tweet_event(event):
  tweet_text = f"""
  @null
  Githubにコミットをプッシュしました。
  [{event['repository']}]
  「{event['commits'][0]['message']}」
  """.strip()
  if 1 < len(event['commits']):
    tweet_text += f"ほか{len(event['commits']) - 1}件"
  tweet_text += f"\n\n{event['commits'][0]['url']}"
  tweet(tweet_text)

def save_id(id):
  with open(FILE_NAME, 'w') as f:
    f.write(id)

def load_id():
  if os.path.exists(FILE_NAME):
    with open(FILE_NAME, 'r') as f:
      return f.readline()
  else:
    return ''

def is_new_id(id):
  return id != load_id()

def parse_commit_log(repo_name, commit):
  return {
    'url': f"https://github.com/{repo_name}/commit/{commit['sha']}",
    'message': commit['message']
  }

def get_repository_description(repo_name):
  url = f"{REPOSITORY_URL}/{repo_name}"
  response = requests.get(url)
  repository = json.loads(response.text)
  return repository['description']

def get_recent_push_event():
  response = requests.get(EVENTS_URL)
  events   = json.loads(response.text)
  recent_event = list(filter(lambda e: e['type'] == 'PushEvent', events))[0]
  repo_name    = recent_event['repo']['name']
  commits      = list(map(lambda c: parse_commit_log(repo_name, c), recent_event['payload']['commits']))
  return {
    'id':         recent_event['id'],
    'repository': get_repository_description(recent_event['repo']['name']),
    'commits':    commits,
  }

event = get_recent_push_event()
if is_new_id(event['id']):
  tweet_event(event)
  save_id(event['id'])
  print('ツイートを投稿しました')
else:
  print('ツイートは不要です')

スクリプトを実行すると概ね以下の手順でツイートされる
1. GithubAPIを叩いて、自身の最新のコミットを含んだイベントログを取得
2. 直近で取得したイベントIDをファイルに保存しておき、そのIDと比較、一致していた場合変更なしとして終了
3. イベントログを元にツイートするテキストを生成
4. TwitterAPIを用いてツイート

所感

  • 本スクリプトを15分おきぐらいにcronで実行すれば、概ねコミット内容がツイートされる
  • Webhookと違ってpull型になるので、リアルタイムにはできない
  • 単にGithubAPIが使いたくて遊んだだけで実用性はあんまり無い