Masteries

技術的なことや仕事に関することを書いていきます.

「Search Inside Yourself─仕事と人生を飛躍させるグーグルのマインド」を読んだ

ちょっと最近, 精神的な面(?)のコントロールが上手く出来ていなくて, そういったことを相談した時に紹介してもらいました. タイトルにもあるように, Googleで実践されている「マインドフルネス」のプログラムをまとめた本です. そのためのエクササイズとして「瞑想」が取り入れられていて, 瞑想というと「なんとなく胡散臭そう...」という印象を持つかもしれませんが, 学術的研究やその成果に基づいて説明が書かれているので, そういった意味での説得力がちゃんとある本だなと思いました.

本によると, EQ(Emotional Intelligence Quotient, 日本語では「こころの知能指数」と表現されている)というものが注目されていて, EQの恩恵としては職務遂行能力の向上やリーダーシップなどがあるそうです. そして昨今の研究により, EQは大人になってからも育てることができるということが判明していて, そのため欧米では社会人向けに, このEQを伸ばすためのセミナーなども開催されているそうです. 本書では, このEQを育てる入り口として, マインドフルネスを用いています.

最初は, 「マインドフルネス瞑想」という1人で行う瞑想からスタートして, 自分自身, 他の誰か, そしてチームへと, マインドフルネスを広げていくような形で構成されています. 基本的には, 序盤の「マインドフルネス瞑想」に基づいてエクササイズの紹介が続いていくので, 都合の良い所だけをつまみ食いするのではなく, 最初から(エクササイズも実践しつつ)読んでいくのが良いのかな, と思います. 今の自分のような, 少し自分自身のメンタルコントロールに苦戦しているという人は, 序盤だけ読んでエクササイズを実践してみる... という形でも良いのかもしれません.

あと, この本を読んでいて思ったのは, 自分自身もこれまで, 無意識のうちに本書で紹介されている「瞑想」のようなモノをしていたのかな...? ということです. 具体的には旅行で, 旅行中に交通機関に乗っている時や, 目的地に向かって歩いている時は, 結構瞑想に近い(?)状態になっていた気がするのですよね... なんというか, 良い意味で心をリラックスさせて, 気持ちを切り替える機会になっていたというか. 実際本書にも, 「歩く瞑想」というエクササイズが紹介されていますし... そういう意味では, 毎日の通勤時間もそういった効果があったのかもしれません.

昨今の新型コロナウイルスの影響で, 旅行(移動)が困難になっていて, そういう時間(機会)を作れなくなっている... というのは, 最近の精神的なトラブルの要因の1つ, なのかもしれません. あとは, 「ずっと自宅で作業している」ということもマイナスに働いているのかな, という気がしています.

ここ数ヶ月, 自宅 = 職場という状況になりつつあるのですが, そういった日々が続くと, どうしても自宅にいるだけで, 常に仕事に関する事が頭の中をよぎってしまう感じがするのですよね... なので, 仕事中はもちろんの事, そうでない時ですら, 仕事はうまくこなせているか? 同僚とうまくコミュニケーション出来ているか? そして期待に答えられているだろうか...? ということを, ずっと延々と考えてしまっている気がします.

こういった状況(?)に銀の弾丸が存在しないのは十分承知しているのですが, とは言え「もしかして...?」というヒントを得た気持ちになりました. 1日数十分の「マインドフルネス瞑想」であれば, やってみて, うまく行かなかったとしても悔いは残らない(?)と思ったので, ひとまず試してみようかな, と思っています. 暫くして, また効果などブログに書けたらいいな, と思っています.

GitHub Actionsで使えるactionを自分で作る

先日, papix/action-cache-s3という, GitHub Actionsのactionを作ったというエントリを書きました.

papix.hatenablog.com

このエントリでは, このactionを作るにあたって得た知見について, 雑に記しておきます.

actionの雛形

折角なので, TypeScriptでactionを書いてみようと思った訳ですが, 何と公式からTypeScript用の雛形が提供されています. 余程の理由がなければこれを使うと良いでしょう.

github.com

...今回, これを使うにあたって初めて知ったのですが, 「Use this template」なるボタン(機能)が存在していて, これをクリックするとそのリポジトリを雛形にして新しいリポジトリをシュッと作ることができるのですね.

f:id:papix:20200517100734j:plain

というわけで, ボタンを押すと...

f:id:papix:20200517100737p:plain

こういう感じでリポジトリの作成画面に遷移します. あとはリポジトリ名など指定して「Create repository from template」をクリックすればOKです.

ローカルでの実行

actionを実装するにあたり, 動作確認を実際にGitHub Actionsで実行するのではなく, 手元のマシンで実行したいと思うはずです. 改修を加える度にcommitして, pushして, 動作を確認する... というのはとても手間です.

そういった際に気になるのが, actionを実装するにあたって利用可能なツールキットであるところのactions/toolkitが提供する, core.getInputcore.getStateで取得できるinput/stateを, 手元の環境で指定できるのか...? という点です. これが出来れば, 例えばTypeScriptのテンプレートを使って実装しているactionであれば, ts-nodeなどを使ってローカルで動作確認をすることができそうです.

結論としては,

help.github.com

のドキュメントにあるように, core.getInputについてはINPUT_をprefixにした環境変数で, core.getStateについては, STATE_をprefixにした環境変数で, それぞれ指定できることができます.

例えば, 環境変数INPUT_SAMPLEtest-inputとしてts-nodeなどでactionを手元で実行すると, core.getInput('SAMPLE')test-inputを返します. また, 環境変数STATE_SAMPLEtest-stateとしてactionを手元で実行すると, 今度はcore.getState('SAMPLE')test-stateを返してくれます.

これで, 余程の事がなければ, GitHub Actionsのactionは手元のマシンで開発し, 動作確認ができると思います.

バージョニング

GitHub Actionsのためのactionのバージョニングについては, 以下のドキュメントが参考になります.

github.com

掻い摘んで説明すると... まず, actionをワークフローで(usesによって)利用する場合, どのバージョンを利用するかを指定しなければなりません.

例えば, GitHub公式のactions/cacheのExample workflowを見てみると, 次のように v1 を指定しています.

    - name: Cache Primes
      id: cache-primes
      uses: actions/cache@v1
      with:
        path: prime-numbers
        key: ${{ runner.os }}-primes

このバージョンニングは, 実態としてはGitのrefを利用しています. 例えば, actions/cache@v1を指定した場合, actions/cache リポジトリにある v1 というタグを参照することになります.

従って, やろうと思えば次のようにshaを直接指定したり, ブランチ名を指定することも可能です(なお, ここでは例としてpapix/sample-actionという架空のactionを開発しているとします).

steps:
    - uses: papix/sample-action@41775a4da8ffae865553a738ab8ac1cd5a3c0044
    - uses: papix/sample-action@master

actionを開発している際, 別のリポジトリで動作を試したい! という時は, これらの方法でバージョン指定すると良さそうです.

但し, このようにmasterブランチを指定することについては, 先程紹介したドキュメントにおいて,

Warning: do not reference master since that is the latest code and can be carrying breaking changes of the next major version.

と記載されています. 「そりゃそうだ」という感じではありますが, masterを指定していると常に最新のactionが利用されることになり, 意図しない変更が含まれる可能性があるので, 基本的にはmasterを参照しないようにしましょう.

...閑話休題. ここまでの話を振り返ると, GitHub Actionsのactionを開発するにあたって, バージョニングは適切なタグを付与することで実現していることがわかります.

例えば, 今開発しているpapix/sample-actionの先頭のcommitをv1.0.0として指定するのであれば, 次のようにしてv1.0.0タグを付与し, それをpushします. そうすると, ワークフローにおいて papix/sample-action@v1.0.0 としてactionを利用できるようになります.

$ git tag v1.0.0
$ git push origin v1.0.0

注意点としては, v1.0.0のタグだけを付与している時, ワークフローにおいて papix/sample-action@v1 というバージョンを指定してactionを利用することはできません. つまり, ワークフローでactionを利用するとき, そのバージョン指定はあくまでrefに従っていて, v1.* の最新のものを v1 として扱う... といった処理は, GitHub Actionsには存在しません.

そこで, 次のようにv1.0.0に加えて, 別途v1のタグを付与し, pushしてあげる必要があります.

$ git tag v1
$ git push origin v1

更に, この後に幾つかcommitを重ねて新しいバージョン(例えばv1.0.1)をリリース(= タグを付与してpush)した場合, v1 がそれを指すように上書きする必要があります(既に存在するv1タグを上書きするので, -f/--forceオプションが必要です).

$ git tag --force v1
$ git push origin v1 --force

会社で教えてもらった情報ですが, この辺りのバージョニングをGitHub ActionsでよしなにやってくれるGitHub Actionsのactionもあります. 必要に応じて利用を検討してみても良いでしょう.

github.com

まとめ

というわけで, 備忘録を兼ねてpapix/action-cache-s3を作る時に得た知見などをまとめました. GitHub Actionsはとにかく便利ですが, 自分でactionを作ることで更に便利することができるので, 良いアイデアがあればactionを作ってみては如何でしょうか.

「1日ひとつだけ、強くなる。」を読んだ

1日ひとつだけ、強くなる。

1日ひとつだけ、強くなる。

プロゲーマーでおなじみ, 梅原大吾(ウメハラ)さんの本.

自分はいわゆる格ゲーは遊ばない(苦手)なのだけれど, そういった世界で戦う「プロゲーマー」と呼ばれる人達には若干興味があって, 紹介エントリなどをちまちまと読だ事が昔あったのでした. そうした時に得た情報と, この本に書かれているウメハラさんの体験談を繋げながら読むことで, 最初から最後まで楽しく一気に読むことができました.

本の内容としては, ウメハラさんのプロゲーマーとしての経験や姿勢, 考え方などを元に, 勝負論, 成長論について述べる... といった感じでしょうか. 当然のように格ゲーの話題がたくさん出てきますが, その説明も前提として丁寧に述べられているので, 「格ゲー全然知らないんだけど?」という人でもスムーズに読めると思います.

個人的には「視点」の話題が印象に残りました:

うまくいかない、結果が出ない、そういった不首尾に終わった結果があって初めて考える。これは少し受け身だと思う。悪い結果が出ていないからといって、考えようとしないのも心もとない。もちろん、悪い結果が出ても対処しようとしないのは論外だ。

①うまくいっているが、視点レベルでより良く修正して場面に反映させる。
②うまくいっているが、場面レベルでより良く修正して場面に反映させる。
③うまくいかなかったので、視点レベルで修正して場面に反映させる。
④うまくいかなかったので、場面レベルで修正して場面に反映させる。

優劣の問題ではなく、いずれのやり方が欠けても良くない。これらは互いに影響を与え合う関係でもあるからだ。

ウメハラさんは, 「一番多いのが④しかやらない人, 次に多いのが④と②だけやる人, 加えて③までやる人はぐっと少なくなり, ①までやる人はほとんどいない」と述べていて, それで言うと確かに自分も④しか出来ていないな... と思ったのでした. 例えば, 「今の現状や手札はこうで, なのでこうしよう」という, 今目の前の状態から考えるだけでなく, 「こういう結果に至るには, この手札を持つ必要があるな」とか, 「こういう手札があったら, どういう事ができるだろう?」とか, そいった感じで別の視点で考える事も必要なのかな... と思うなどしました. とはいえ, そういった思考には体力と健全な精神衛生が必要と思っていて(それらがないと, そういった事を考える余裕がないと思っている), まずはそこからかな...

その他, 成長論や自信について, 「こうではないか?」と個人的に考えていた事をウメハラさんも述べられていて, その辺りは実践していくにあたって自信を持てた気がします. 例えば,

結局、苦手なことから目を背けていると自信を持てない、ということだと思う。苦手に挑戦していれば、たとえうまくできなくても、挑戦していることで自分を肯定的に見られるようになる。それが自信になる。

という所とか. 最近は, これまで「苦手だし, なんとなく...」でやっていたことを, きちんと調べてメモして, 知見と経験を蓄積するような試みをしているので, こういった事も継続して自信に繋げることが出来ればいいなと思います.

単純に読み物として面白いですし, 「成長」について悩みがある人にとっては良い示唆が得られる本だなと感じました. これより前に執筆された, 『勝ち続ける意志力: 世界一プロ・ゲーマーの「仕事術」』もKindleで買っている(そしてそのまま積んでいる...)ので, 今度はそちらも読みたいですね.

GitHub ActionsでS3にキャッシュを保存できるpapix/action-cache-s3を作りました

先日, こちらのエントリでGitHub公式のactions/cacheを使わずに, 自前でS3を使ってキャッシュする方法を紹介しました.

papix.hatenablog.com

「これ, actionに切り出して再利用できるようにしてみては?」という意見を頂いたので, 日曜日にサクッと実装してみました.

github.com

S3にキャッシュをするので, 予めS3バケットを作り, そこに読み書きが可能なAWS_ACCESS_KEY_ID/AWS_SECRET_ACCESS_KEYをリポジトリ/オーガニゼーションのSecretsで指定した上で, 次のようなワークフローを記述することで利用できます.

on: push

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v2

    - uses: papix/action-cache-s3@master
      env:
        AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
        AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
        AWS_DEFAULT_REGION: ap-northeast-1
      with:
        bucket: cache-s3-test-bucket
        key: node_modules-${{ hashFiles('package.json') }}
        path: node_modules

一応, actions/cacheとほぼほぼ似た使い勝手になるように作っています(実際にS3へキャッシュする部分をジョブの最後に実行するようにしたりとか). ...但しドキュメントやテストはほぼ未整備ですし, actions/cacheにあるrestore-keysのような仕組みもまだないので, これらは追々整備していこうと思います.

papix.hatenablog.com

こちらのエントリでも紹介しましたが, GitHub公式のactions/cacheは現状若干クセがある... と言えると思っています. その辺りで困っている方は是非使ってみていただければと思います(Pull Requestも歓迎です!).

あと, これを作るにあたっていろいろとGitHub Actionsのactionを実装する際の知見を得ることが出来たので, これらについて別エントリでご紹介しようと思います.

GitHub Actionsでactions/cacheを使わずS3で必要なファイルをキャッシュする

papix.hatenablog.com

先日, 「GitHub Actionsの知見ご紹介」でactions/cacheが意図通り動作しないケースがある, ということをご紹介しました. 今回は, actions/cacheの代わりにS3を使ってキャッシュを実現する方法をご紹介します. ...まあ, ご紹介しますというか, まあ普通にawsコマンドを使って必要なファイルをS3に置いたり引っ張ってきたりするだけなのですが.

ここでは, 例としてcpanfile.snapshotを元にして, Perlのモジュールがインストールされるディレクトリ(local)をS3でキャッシュする例をご紹介します. Node.jsであれば, cpanfile.snapshotpackage.json, localnode_modulesと読み替えればOKです.

前提として, 適当なS3バケット(以下の例では, sample-cache-bucketという名前としました)を用意しておいてください. また, S3への読み書きが可能なIAMアカウントを用意して, そのAccess Key IDとSecret Access KeyをGitHubのSecrets(リポジトリのSettingsSecrets)で, それぞれAWS_ACCESS_KEY_IDAWS_SECRET_ACCESS_KEYという名前で登録しておく必要があります.

env:
  cache-bucket: sample-cache-bucket
  cache-directory: perl

jobs:
  prepare:
    runs-on: ubuntu-latest
    steps:

    - name: Configure AWS Credentials
      uses: aws-actions/configure-aws-credentials@v1
      with:
        aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
        aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
        aws-region: ap-northeast-1

    - name: Fetch cached perl modules
      run: |
        if [[ $(aws s3 ls s3://${{ env.cache-bucket }}/${{ env.cache-directory }}/${{ hashFiles('cpanfile.snapshot') }}.tar.gz | wc -l) > 0 ]]; then
          aws s3 cp --no-progress s3://${{ env.cache-bucket }}/${{ env.cache-directory }}/${{ hashFiles('cpanfile.snapshot') }}.tar.gz perl-modules.tar.gz
          tar -zxf perl-modules.tar.gz
        else
          echo "Cache not found"
        fi

    # ここで必要に応じてライブラリのインストール(carton install, npm installなど)を実行する

    - name: Cache perl modules
      run: |
        if [[ $(aws s3 ls s3://${{ env.cache-bucket }}/${{ env.cache-directory }}/${{ hashFiles('cpanfile.snapshot') }}.tar.gz | wc -l) > 0 ]]; then
          echo "Cache already exists"
        else
          tar -zcf perl-modules.tar.gz local
          aws s3 cp --no-progress perl-modules.tar.gz s3://${{ env.cache-bucket }}/${{ env.cache-directory }}/${{ hashFiles('cpanfile.snapshot') }}.tar.gz
        fi

...少なくとも, runs-onubuntu-latestの場合, デフォルトでawsコマンドが/usr/local/bin/awsに用意されています. 2020年5月現在バージョンは1.18.37となっているようで, 最新の2系ではないのですが, 例なので今回はこれをそのままを使うことにしましょう(より新しいバージョンのawsコマンドが必要であれば, 別途インストールしてください).

後はaws-actions/configure-aws-credentials@v1を利用して適切にAWSアカウントの認証(ここでSecretsで設定したAWS_ACCESS_KEY_IDAWS_SECRET_ACCESS_KEYを利用します)をした上で, awsコマンドを使って S3からファイルを撮ってくる/ファイルを設置するだけです.

これで,

  • cpanfile.snapshotに対応するキャッシュがあれば...
    • S3からこれをダウンロードして利用する
    • 必要なライブラリは全てキャッシュから復元されているはずなので, ライブラリのインストールをしても差分なしですぐに完了する
  • cpanfile.snapshotが書き換えられるなどしており, 対応するキャッシュがないなら...
    • ライブラリのインストールを実行して, その結果を最後にS3にアップロードする
    • 2回目以降はキャッシュが利用されるようになる

...という挙動が実現できます.

S3を使えば, 前のエントリで紹介したactions/cacheのハマりポイントを意識する必要はありませんし(2〜3週間運用していますが, キャッシュの取得にミスした事例はほぼほぼなくなった), 必要があればAWSのWebコンソールなどを使って, キャッシュを削除したりできるので, 適切なS3バケットが用意できるのであればむしろこちらの方が便利なのでは...? という気がしています.

一方で, 当然ながら別途S3の料金が必要になるのはデメリットですね. なるべく料金を節約できるよう, ライフサイクルルールを設定するなどしつつ利用すると良さそうです.