くりにっき

フルスタックキュアエンジニアです

actions/upload-artifactとactions/download-artifactは同時にバージョンアップする必要がある

前置き

actions/upload-artifactdownload-artifact がそれぞれv4になりました。

github.blog

個人リポジトリ.github/dependabot.yml で下記のような自動更新設定を入れていたのでそれぞれバージョンアップのPRが作られました。

updates:
  - package-ecosystem: github-actions
    directory: /

しかし、片方ずつバージョンアップするPRだとCIがコケてしまったので同時にバージョンアップする必要がありました。

github.com

github.com

手でバージョンアップしても良かったのですが、今後の事も考えて自動化しました。

実際の設定

下記のように複数のactionを1つのグループとして扱うことでDependabotで同時にバージョンアップするすることができます。

    groups:
      artifact-actions:
        patterns:
          - "actions/upload-artifact"
          - "actions/download-artifact"

github.com

参考リンク

github.blog

https://docs.github.com/en/code-security/dependabot/dependabot-version-updates/configuration-options-for-the-dependabot.yml-file#groups

実際に作られたPR

ヨシ!

github.com

rbs_collection.lock.yamlをGitHub Actionsで自動updateする

ruby-jp slackでそういう需要があるので作った

ワークフローの設定

最低限いるのはこの辺。必要に応じてslack通知とか足してください *1

name: rbs-collection-updater

on:
  schedule:
    - cron: "0 0 1 * *" # Run monthly
  workflow_dispatch: # Run manually

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - uses: actions/checkout@v4

      - uses: ruby/setup-ruby@v1
        with:
          # TODO: 適宜バージョンを指定する。(リポジトリに.ruby-versionや.tool-versionsをコミットしているなら不要)
          # ruby-version: "3.2" 

          bundler-cache: true

      - run: bundle exec rbs collection update

      - uses: actions/create-github-app-token@v1
        id: app-token
        with:
          app-id: ${{ secrets.GH_APP_ID }}
          private-key: ${{ secrets.GH_APP_PRIVATE_KEY }}

      - uses: peter-evans/create-pull-request@v5
        with:
          token: ${{ steps.app-token.outputs.token }}
          committer: GitHub <noreply@github.com>
          title: "Update rbs_collection.lock.yaml"
          commit-message: "Run `bundle exe rbs collection update`"

実際に作られたPR

github.com

botの名前がsue445-bundle-update-prになっているのはbundle update PR用途で使ってたGitHub Appを流用しているため

事前に必要なもの

GitHub App

GitHub Actionsでデフォルトで使える secrets.GITHUB_TOKEN でPRを作成するとそのPRに対するjobが実行されない*2ので、PRを作りたい時だけは使わない方がいいです。

そこで別のtokenを使うことになるのですがGitHub ActionsでPersonal Access Token(PAT)を使うのはセキュアじゃない*3のでGitHub App経由でTokenを発行する(通称App Token)のが定番です。

github.com

docs.github.com

GitHub Actions上でPRを作るためにはGitHub Appに下記のパーミッションがあるといいでしょう

  • Contents: Read and write
  • Pull requests: Read and write

作成したAppのIDと秘密鍵はsecrets経由で渡しています。

*1: https://github.com/sue445/doorkeeper_jp/blob/main/.github/workflows/rbs-collection-updater.yml だとslack通知を入れている

*2:jobの無限実行を防ぐためのGitHub Actionsの仕様。c.f. https://sue445.hatenablog.com/entry/2020/08/31/081447

*3:アクセス可能なリポジトリや有効期限が無制限のPATが漏れると死

MDの使用デッキで振り返る2023年 #遊戯王AC

はじめに

これは 遊戯王 Advent Calendar 2023 の1日目です。

adventar.org

sue445と遊戯王

遊戯王のカードゲームは

  • マスターデュエル(以下:MD)
  • OCG(紙)
  • ラッシュデュエル(紙)
  • ラッシュデュエル(Switch版) *1

をゆるく触っています。

MDはリリース日からプレイしていて、Switchによると1775時間以上プレイしているようです。

最近のランクマッチ(以下:ランクマ)ではダイヤモンド〜マスター帯をさまよってます。

前置き

遊戯王のアニメは初代からずっと見てましたが、カードゲームとしての遊戯王遊戯王デュエルモンスターズ レガシー・オブ・ザ・デュエリスト:リンク・エボリューション (以下:LotD)で本格的に入門しました。

LotDの時からの習慣なのですが、ネット対戦*2する時には日々の勝敗数と勝率を記録しています。

MDでも勝敗数はメモっているのでこの機会に2023年に使ったデッキを晒してみようと思います。

解説

僕がMDでランクマやイベントでの対戦を行う場合、先行後攻ごとにそれぞれ勝敗をメモ帳に「正」の字でメモるようにしています。(「み」と書いてるのは御巫デッキを使っていたため)

勝敗をつける時のオレオレルールとして下記を意識しています。

  • 自分が何もしてないのに勝ってしまった場合(例:相手の先攻ターンでこっちが何も手札誘発とか使ってないのに相手が勝手にサレンダー)はノーカン。(戦績つける時にこの手の意図しない勝ち星があるとノイズになって嫌なので)
  • 通信切断による勝利はその時の流れによって決める
    • こっちの優勢な時に切断が起きた場合には勝利扱い。(相手のサレンダーとみなす)
    • こっちが不利な時に切断が起きた場合には敗北扱い。(普通に考えて自分が有利な時に切断するわけないのでMD側の障害とみなす)

ランクマ1戦ごとにスプレッドシートに記録するのは大変なので、1日の終わりか翌日始めにスプレッドシートにまとめて勝敗数を記録しています。

スプレッドシートにデータが貯まることで集計して活用しやすくなります。

実際にまとめたやつ

2023年分だけを公開しておきます。

https://docs.google.com/spreadsheets/d/1CG6LAA5yHoXB3fCD39FJgekA6VIIbtMXbTDp057gVsM/edit#gid=862180514

2023年総合

圧倒的にヌメロンエヴァイユが多いw

去年の11月くらいから使い始めて今年9月のリミットレギュレーションの改訂 *3No.86 H-C ロンゴミアントが禁止になるまでずっと使っていました。

10ヶ月間で色々調整はしてきたけど一番最後に使ってたのはこれです。

ちなみにヌメロンエヴァイユの前は壊獣カグヤをよく使ってたし、LotD時代に一番使ってたのはサイバー・ドラゴンデッキなので後攻デッキが好きなのだと思います。

ロンゴミ禁止以降は下記で紹介されている蟲惑魔春化精を一番使っていると思います。

note.com

月ごとに振り返り

開催されたイベントとその時に使ったデッキを見ながら振り返ってみます。

一応リリース当初からイベントは全部やっていてフェスでは報酬を完走するところまではやっていますが、デュエルトライアルは記録してないのでここに書いてるイベントは多少漏れがあると思います。

1月

最初に書いたように8月まではランクマはずっとヌメロンエヴァイユを使ってたので、ランクマで使っていたデッキは基本的に省略。

この月のイベントはテーマクロニクル

僕はオルフェゴールでイベント完走

2月

この月のイベントは2つ開催

レジェンドアンソロジーサイバー・ドラゴンデッキを使用

飛翔するGフェス エクシーズフェスティバルはランクマで使ってたヌメロンエヴァイユで完走。

飛翔するGが規制される *4 前に完走したのでデッキに飛翔するGが入っています

3月

スプライトが出た後なのでランクマはスプラツインも使ってたけど、やっぱりヌメロンエヴァイユの方が多かったです。

この月のイベントはデュエリストカップ

僕はスプラツインを使用。

4月

当時の環境を席巻したティアラメンツが登場した月。

僕もランクマでイシズティアラメンツは少し使ってたけどやっぱりヌメロンエヴァイユの方が多かったです。

この月のイベントはアトリビュート4。

僕は蟲惑魔で完走。

5月

ランクマではヌメロンエヴァイユの合間にウォークライやインスペクト・ボーダーも使用。

この月のイベントはYu-Gi-Oh! World Championship 2023。

ランクマで使ってたヌメロンエヴァイユを使ってたと思います。

6月

ランクマだと一瞬烙印ビーステッドを使ってたようだけど一番多かったのはやっぱりヌメロンエヴァイユ

この月のイベントは盛りだくさん

レジェンドアンソロジーは表サイバー流で完走。

アニメGXが好きなのでついつい自分の中のヘルカイザーが目を覚ます。

シンクロ(しない)フェスティバルはウォークライで完走。

7月

紙で使ってた蟲惑魔ストラクがこの月にMDに実装されて狂喜乱舞した記憶。

ランクマはヌメロンエヴァイユと蟲惑魔春化精が半々くらい。

この月のイベントは群雄割拠フェスティバル。

僕はラビュリンスで完走。

8月

クシャトリラが実装されたのでクシャイシズティアラメンツを使ってたことが多かった気がします。

ロンゴミアントの禁止が発表されてからはヌメロンエヴァイユで最後の追い込みをして、ギリギリマスター帯に到達してました。

この月のイベントは闇vs光フェスティバル

闇はラビュリンス、光はエルドリッチを使ってました。(後者はスクショ失念)

9月

御巫が実装された月。

天底の使徒 が制限復帰したので天底ラビュリンスを一番使ってた気がします。

この月のイベントは2つ。

群雄割拠フェスティバルはモンスターをほとんど入れないバーンデッキで完走。(群雄割拠とは...)

フュージョン×エクシーズフェスティバルはサイバー・ドラゴンで完走。

10月

この月は忙しくてあんまりランクマやってないな...

この月のイベントはデュエリストカップ

イベントでは蟲惑魔春化精を使ってた模様。(スクショ失念)

11月

ランクマでは蟲惑魔春化精を使用。

この月のイベントはリチュアルフェスティバル。

壊獣御巫で完走。

 

この記事を書いてるのが11月なのでここまで。

FAQ

Q. なんで勝敗数をつけてるの?

なんとなくやり始めたら惰性でずっと続いてしまった。

2日目

それはどうかなと言えるデュエル哲学【EXW】 さんのエントリです。

note.com

*1: https://www.konami.com/yugioh/rushduel_game_gorush/

*2: LotDにはMDでいうところのランクマッチというのは存在せず(おそらく)ランダムでマッチング

*3: https://twitter.com/YuGiOh_MD_INFO/status/1693495758056743295

*4: https://twitter.com/YuGiOh_MD_INFO/status/1628255686269472768

ISUCON 13に1人チームで出場して再起動試験でfailした話

tl;dr;

タイトルが全て

今年の準備

ISUCONの前の週に Google Cloud Next Tokyo ’23 に登壇した関係で今年の準備期間は実質1週間程度でした。

とりあえず勘を取り戻すために下記の素振りをしてました。

github.com

github.com

リポジトリ

競技用のリポジトリ

github.com

ISUCON用の汎用Itamaeレシピ集

github.com

PRとDatadogを見ながら当日やったことを振り返り

当日10:00〜18:00のDatadog晒し

sinatraAPM

競技中はここを見るのが一番多かったです。

サーバ全台

puma

pumaのメモリ以外のメトリクスが後半しかないのは、DatadogのPuma Integrationの設定を入れたのが後半なため。

MySQL

具体的にやったこと

github.com

CloudFormationから起動した直後のインスタンスにベンチマーカーを実行(スコア:4148)

いつものスニペットをコピーして参照実装をGoからRubyに変更(スコア: 3781)

github.com

この時点でRuby 3.3.0-devにしてます。

Sentryとddtrace(DatadogのAPM)を有効化(スコア:3497)

github.com

ここでようやくスタート地点

rubocop-isucon導入(スコア:3389)

github.com

いつもならこの時点でN+1がどれくらいあるかindexを貼る箇所を見つけているのですが、今までとコードの書き方が微妙に違うせいでASTの構成が変わって Isucon/Mysql2部署のcop が全く動かなかったのがショックだった、、、

GET /api/user/:username/icon : DBにある画像を逃がす(スコア:3827)

Datadogを見たら GET /api/user/:username/icon が明らかにボトルネックになってたのでこいつの改善に着手。

エンドポイントを選んでDurationの降順してボトルネックを発見。

小ネタですが https://github.com/sue445/isucon13-20231125/blob/main/ruby/config/ddtrace_init.rb#L55-L65 のようなモンキーパッチをあててSQLの生クエリ(プレースホルダ? が入ってないやつ)をDatadogに送信してexplain取りやすくしてます。(ユーザが入力したパスワードもDatadogに全部生で送信されるので本番アプリには絶対にいれたらダメなパッチ)

GET /api/user/:username/icon : 画像をnginxで返す by sue445 · Pull Request #7 · sue445/isucon13-20231125 · GitHub

ソース見たらDBに画像が保存されてたのでnginxで返そうとしたのですがここで1時間以上手こずったと思います。

ChatGPTに聞きながらやってもいい感じのnginxの設定が書けずに最終的にローカルに保存した画像をsinatraで返すようにしました。

最終的にこんな感じでボトルネック改善したのを確認。

これでもまあ悪くないので1時間もかけずに早いところ諦めるべきだったね、、、(1人チームだとハマった時に無限に時間が溶ける)

fill_user_responseでDBの画像を使わないようにする(スコア:4518)

github.com

最後の方で気づいたけど画像を保存する前に計算したhashをDBに入れた方がよかった。

2台目のサーバをDB専用として投入(スコア:6893)

github.com

ここも微妙にハマったやつ。

デプロイ時に1台目のサーバのMySQLを止めて2台目のサーバのみMySQLを起動してるのに、デプロイ後になぜか1台目のサーバも止めたはずのMySQLが復活してむっちゃわけ分からずにハマってました。

最終的にはserviceファイルのAfterとRequiresが原因とわかって消したんですが、そうしたらPowerDNSが使ってるMySQLにも影響して復活させました

MySQLのスローログを無効化(スコア:7028)

github.com

どうせ見ないので無効化した

index追加祭(スコア:7132)

github.com

github.com

github.com

github.com

POST /api/initialize でやってるTRUNCATE TABLEだとindexが消えなくて、かといってMySQLだと ADD INDEX IF NOT EXISTS のような冪等性のあるDDLが分からなかったのでinitializeで実行されるsqlファイルに入れるのを諦めて手動で投入することにしました。(gitの履歴としては残したいのでこういうファイルだけcommit)

livecomment_modelがnilってNoMethodErrorになったので修正

index追加中にこういうエラーに遭遇したので修正。こういう時sentry使ってると検出できて便利っすね。( https://sentry.io のqueueが詰まってたせいか分からないけど最初の方は全然エラーが通知されなくてつらかったけど)

github.com

github.com

3台目投入(スコア:7228)

github.com

app専用として3台目を投入して負荷分散しようと思ったんですが、appがローカルのPowerDNSに依存しててそのPowerDNSを別サーバに動かすのが手こずりそうだったので実際の負荷分散は後回しにすることに。

17:21頃に再起動試験

appを1台で動かす前提にする(スコア:6949)

この時点で残り時間1時間きってたので危険な変更はしないようにしました

github.com

最後にDatadogとか諸々無効化(スコア:10663)

github.com

最終スコア

isucon.net

10,663 sue445.members.count==1 (再起動後スコア0)

ええ。マジ、、、

競技時間中に再起動試験して問題なかったのに、追試の再起動試験でスコア0になるとは思わなかった。

来年に向けて

ruby-wasm-vdomで雑なオレオレツールを作った

作ったもの

https://sue445.github.io/annict-vod-search/

github.com

モチベーション

最近縁があって Annict の編集者*1 になって、気がついた時に各アニメの配信サイトの情報を登録しています。

その時にいちいち複数の配信サイトでアニメのタイトルを検索するのが大変なので一箇所で検索できるようにしたくて作りました。(製作時間は2〜3時間)

使った技術

いつもだとこの手の雑なページはVue.jsを使うことが多いのですが、今回は面白全部 *2ruby.wasmを使ってみました。

ruby.wasmで仮想DOMを扱うためにruby-wasm-vdomを利用しています。

ruby-wasm-vdomについては下記を参照。

github.com

qiita.com

感想

  • 使い慣れたRubyで書けるのは便利
  • ヒアドキュメントでJSXっぽく書けるのは面白い *3
    • しかし入力値をそのまま出力するとXSSが発生して こういう対応 を自前でやる必要があって大変。(Railsだとデフォルトでいい感じにしてくれるのであまり気にしてなかった)
  • wasmの中でエラーが起きた時にどの行でエラーが出たかとかがぱっと分からないのでデバッグが大変だった
  • あまりドキュメントがなかったけど https://github.com/getty104/ruby-brainfuck-interpreter が参考になった

*1:データベースにアニメ情報を自由に追加できる人

*2:面白半分の2倍

*3:https://github.com/sue445/annict-vod-search/blob/be8a262271f5e26f4cfe0618e41f9e7f8ba6e008/docs/src/app.rb#L24-L42

Google Slidesで作ったスライドをSpeakerDeckに公開するためのTips

前置き

普段発表用の資料は Google Slides で作成し、Google SlidesでPDFにエクスポートした後に https://speakerdeck.com/ にアップロードしています。

長年の暗黙知が積み重なってきたのでメモ。

フォントをM PLUS 1pにする

Google SlidesだとデフォルトのフォントがArialとかになっていますが、このフォントだとPDF化した時にレイアウトが崩れたり文字が掠れるため、PDF化する前提なら初手でM PLUS 1pにするのが無難です。

参考URL

speakerdeck.com

note.com

絵文字は使わない

絵文字が含まれるPDFをSpeakerDeckにアップロードしたらいつまで経ってもスライドが作成されなかったり、作成されたスライドもダウンロードできない(ダウンロードできてもPDFがぶっ壊れていて表示できない)という事象がありました。(今はなおってるかも?)

そのため、自分のスライドではなるべく絵文字は使わないようにしています。(どうしても使いたい場合には絵文字を画像としてスライド貼り付ける)

ソースコードを貼り付ける時にいい感じにシンタックスハイライトを効かせるやつ

いくつかあるので紹介

SlidesCodeHighlighter

一番よく使うやつ。ソースコードをテキストとして貼り付けたい場合にはこれが一番使いやすかった。

romannurik.github.io

日本語の説明

monomonotech.jp

Carbon

carbon.now.sh

オフラインでも動くのと、コードを画像として貼り付けるので見る環境によって変わらないのがポイント。

VSCodeなど

VSCodeなどで書いてリッチテキストでコピペ

個人メモ用のNotionを作った

sue445.notion.site

モチベーション

業務で Notion を使ってるんだけど、データベース機能が圧倒的に強いので個人メモ用にもNotionを使ってみることにした。

maekdownで書ける方が嬉しいので esa は引き続き使い続けるつもりです。

コンテンツ

現時点で作ってるものは下記

アイドルランドプリパラ 楽曲リスト

sue445.notion.site

アプリのリリース以降各種攻略サイトが全然更新されなくて困ったので自分用に作った。(特に楽曲ごとのノーツ数がまとまってるサイトがなくて困った)

プリティーシリーズイベントDB

sue445.notion.site

各演者がどのライブに出演していたかをたまに調べたくなるのと、そのライブのBlu-rayとかが発売されているかどうかがまとまってるページがなかったので作った。

プリティーシリーズのライブ、2021年まではそれなりに円盤が発売されていたんだけど最近は発売されないことが多くてつらい...