<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0"><channel><title>清水川Web</title><link>https://www.freia.jp/taka</link><description>清水川Webは、Python関連の技術的な事についての個人的メモや、清水川の日々の雑記を公開しています。</description><language>ja</language><copyright>Takayuki SHIMIZUKAWA</copyright><lastBuildDate>Mon, 23 Feb 2026 23:59:00 -0000</lastBuildDate><item><title>PyCon mini Shizuoka 2026 に参加しました</title><link>https://www.freia.jp/taka/blog/2026/02/pyconshizuoka2026/index.html</link><description>&lt;section id=pycon-mini-shizuoka-2026&gt;

&lt;p&gt;2月21日に静岡市で開催された、PyCon mini Shizuoka 2026 に参加しました。
昨年2月の同イベントでは私が &lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html"&gt;&lt;span class=doc&gt;キーノート登壇&lt;/span&gt;&lt;/a&gt; させていただきましたが、あっという間に1年たちました。&lt;/p&gt;
&lt;p&gt;今回は一般（パトロン）チケットとして参加しつつ、副業先のFlying Duck社がスポンサーブースを出していて、そこのお手伝いもしました。&lt;/p&gt;
&lt;figure class=align-default id=id13&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/opening1.jpg"&gt;&lt;img alt="../../../../_images/opening1.jpg" src="https://www.freia.jp/taka/_images/opening1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニングの様子&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;2トラックでトーク10本以上にLT4本と、今年も盛りだくさんなイベントでした。
今回は公式パーティーがイベント会場で行われて、サプライズもあり大いに盛り上がりました。
イベントは去年と同じ会場 &lt;a class="reference external" href="https://coc-shizuoka.jp/"&gt;静岡市コ・クリエーションスペース&lt;/a&gt; です。&lt;/p&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon mini Shizuoka 2026&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://shizuoka.pycon.jp/2026/"&gt;https://shizuoka.pycon.jp/2026/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;2026年2月21日(土) 10:00 〜 18:00&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;静岡市コ・クリエーションスペース &amp;amp; B-nest&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;私の参加時のメモ（blog元ネタ）が &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2026"&gt;PyCon mini Shizuoka 2026 - 清水川のScrapbox&lt;/a&gt; にあります。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id3&gt;
&lt;h2&gt;総括&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;2トラックあって、どちらを聞くか悩むこともありましたが、迷ったらスポンサーブースで聞く、という感じにしていました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;会場は運営メンバーが他のイベントでも利用させてもらっていて、静岡市が無料で提供しているとのこと。キャンプをイメージしたメインルームはとてもきれいで使いやすかったです。WiFiも完備。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;キーノートは静岡出身の @aodag さん。以前からキーノートやりたいとアピールしていたとか何とか。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;飲み物やお昼ご飯の提供などは無し。スタッフがランチマップを提供してくれていました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;公式パーティーが会場内で開かれて 18:20 スタート。去年は懇親会が別会場（クラフトビールのお店）でしたが、今年は会場そのままで行われた（ビールあり）。初めて会う方と話すきっかけがたくさんあって良かったです。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スポンサーブースがいくつか。今回Flying Duck社はブース用にロゴ入りテーブルクロスを用意しました。PyCon JP やBeProudでのブース出展ノウハウが活かされました。さくらインターネットさんのブースはクオリティ高かったな。&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;開場〜オープニング&lt;/h2&gt;
&lt;p&gt;10時開場。昨年と同じ &lt;a class="reference external" href="https://coc-shizuoka.jp/"&gt;静岡市コ・クリエーションスペース&lt;/a&gt; 、静岡駅から徒歩10分ほどです。地下道をうまく使って到着。&lt;/p&gt;
&lt;figure class=align-default id=id14&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/venue2.jpg"&gt;&lt;img alt="../../../../_images/venue2.jpg" src="https://www.freia.jp/taka/_images/venue2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;会場の様子&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;ConnpassのQRコードで受付を済ませ（手軽で良いですね）、受け取った名札に手書きで名前を書くスタイル。&lt;/p&gt;
&lt;p&gt;10時半からオープニング。スタッフからイベントの案内がありました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h2&gt;キーノート&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;10:45 〜&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Atsushi Odagiri (@aodag)&lt;/li&gt;
&lt;li&gt;&lt;p&gt;資料: &lt;a class="reference external" href="https://github.com/aodag/pycon-mini-shizuoka-2026/blob/main/slide.org"&gt;https://github.com/aodag/pycon-mini-shizuoka-2026/blob/main/slide.org&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default id=id15&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/keynote3.jpg"&gt;&lt;img alt="../../../../_images/keynote3.jpg" src="https://www.freia.jp/taka/_images/keynote3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;キーノートの @aodag さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;キーノートは、スクリプトとして使うのに知っておきたいPythonの使い方。
着眼点が最近のAIやデータ系でなく、Webですらなく、Pythonの基本という感じで良かった。
参考文献がPython公式ドキュメントのみ。&lt;/p&gt;
&lt;p&gt;振り切り方が良いですね。&lt;/p&gt;
&lt;p&gt;詳しい内容は &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2026"&gt;PyCon mini Shizuoka 2026 - 清水川のScrapbox&lt;/a&gt; のメモを参照ください。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id6&gt;
&lt;h2&gt;ランチ&lt;/h2&gt;
&lt;p&gt;キーノートが終わったら午前中おわり。
スタッフが用意してくれた &lt;a class="reference external" href="https://www.google.com/maps/d/u/4/edit?mid=1C4EJXgTE4CnC1-HQOO-D4A0xqCP2zdc&amp;amp;usp=sharing"&gt;グルメマップ&lt;/a&gt; を頼りに各自ランチに出かけていきました。&lt;/p&gt;
&lt;figure class=align-default id=id16&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lunch1.jpg"&gt;&lt;img alt="../../../../_images/lunch1.jpg" src="https://www.freia.jp/taka/_images/lunch1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;のっけ家、並んでたのでまちながらメニュー検討&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id17&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lunch2.jpg"&gt;&lt;img alt="../../../../_images/lunch2.jpg" src="https://www.freia.jp/taka/_images/lunch2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;のっけ家、まぐろづくし丼&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id18&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/gelato1.jpg"&gt;&lt;img alt="../../../../_images/gelato1.jpg" src="https://www.freia.jp/taka/_images/gelato1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ななやの、ジェラート。7番が一番濃い&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id19&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/gelato2.jpg"&gt;&lt;img alt="../../../../_images/gelato2.jpg" src="https://www.freia.jp/taka/_images/gelato2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ほうじ茶+抹茶7番&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;ななやの7番は、3年くらい前に知ってからずっと狙ってましたが、これまで日が合わず行けていませんでした。この日は日中とても暖かくて上着不要なくらいだったこともあり、とても美味しい濃い抹茶ジェラートを楽しめました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id8&gt;
&lt;h2&gt;トーク&lt;/h2&gt;
&lt;p&gt;2トラック6セッション + ブース出展ショートトーク + LT という構成でした。&lt;/p&gt;
&lt;section id=pythonweb&gt;
&lt;h3&gt;PythonでWeb地図アプリを作ってみよう（ぴっかりん）&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;13:20 〜 トラック2&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ぴっかりん&lt;/li&gt;
&lt;li&gt;&lt;p&gt;レベル：Basic / カテゴリ：可視化&lt;/li&gt;
&lt;li&gt;&lt;p&gt;資料: &lt;a class="reference external" href="https://speakerdeck.com/ra0kley/pythondewebdi-tu-apuriwozuo-tutemiyou"&gt;https://speakerdeck.com/ra0kley/pythondewebdi-tu-apuriwozuo-tutemiyou&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default id=id20&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk11.jpg"&gt;&lt;img alt="../../../../_images/talk11.jpg" src="https://www.freia.jp/taka/_images/talk11.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ぴっかりんさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;静岡県は3Dデータの作成に力を入れていて、 &lt;a class="reference external" href="https://3dview.tokyo-digitaltwin.metro.tokyo.lg.jp/"&gt;東京都デジタルツイン3Dビューア&lt;/a&gt; でみれるということで紹介されてました。
また、3次元空間を2次元の地図で表示するのに、「Webメルカトル」という図法があって、これを作ったのがGoogleの人。北極点南極点付近をカットすることで2次元に展開したときの歪みの影響を減らしているらしい。なるほどーー。&lt;/p&gt;
&lt;p&gt;今回のトークでは、 &lt;a class="reference external" href="https://pypi.org/project/leafmap/"&gt;leafmap&lt;/a&gt; を使ってJupyter上でインタラクティブな地図を表示する紹介でした。
タイル地図をベースに、マーカーを重ね合わせて表示など、Pythonで地図アプリが作れるのはとても便利そう。&lt;/p&gt;
&lt;p&gt;コード3行で地図が出る！&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=kn&gt;import&lt;/span&gt; &lt;span class=nn&gt;leafmap&lt;/span&gt;
&lt;span class=n&gt;m&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;leafmap&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Map&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;center&lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=mi&gt;40&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;140&lt;/span&gt;&lt;span class=p&gt;),&lt;/span&gt; &lt;span class=n&gt;zoom&lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=mi&gt;4&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;m&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;トーク中にさっそく &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;uv&lt;/span&gt; &lt;span class=pre&gt;init&lt;/span&gt;&lt;/code&gt; して &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;uv&lt;/span&gt; &lt;span class=pre&gt;add&lt;/span&gt; &lt;span class=pre&gt;leafmap&lt;/span&gt;&lt;/code&gt; でインストールして試してみました。
Windowsターミナルでは、Jupyter上でのように地図は表示されず。
&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;m.to_html("index.html")&lt;/span&gt;&lt;/code&gt; でHTMLとして出力してブラウザで開いたら見れました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=pydanticjsonvalidation-takanori-suzuki&gt;
&lt;h3&gt;Pydanticで複雑なJSONを一発でValidation（Takanori Suzuki）&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;15:50 〜 トラック1&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Takanori Suzuki&lt;/li&gt;
&lt;li&gt;&lt;p&gt;レベル：Advanced / カテゴリ：Pythonコア, プログラミングノウハウ（RPA, 自動化）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;資料: &lt;a class="reference external" href="https://slides.takanory.net/slides/20260221shizuoka/"&gt;https://slides.takanory.net/slides/20260221shizuoka/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk31.jpg"&gt;&lt;img alt="../../../../_images/talk31.jpg" src="https://www.freia.jp/taka/_images/talk31.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;/figure&gt;
&lt;p&gt;学習教材の入力フォーム形式定義を JSON + JSONSchema で行っていたけど、共通部分もそれぞれで定義する必要があり、 &lt;a class="reference external" href="https://docs.pydantic.dev/latest/"&gt;Pydantic&lt;/a&gt; に切り替えたという話でした。&lt;/p&gt;
&lt;p&gt;Pydantic、ちょっとしたことのために導入するにはフットプリントが大きそうで避けたい気もしますが、JSONのデータ構造をPythonコードで表現できて、IDE補完も効くようになり、バリデーションもできるので、便利ですよね。
JSONをDBに格納することも多いので、そのデータ構造を保証するバリデーションに使いたい。&lt;/p&gt;
&lt;p&gt;質疑応答でも、Pydanticにしたことでテストがしやすくなった、と言及されてました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id9&gt;
&lt;h3&gt;その他のトーク&lt;/h3&gt;
&lt;p&gt;今回参加したトークのメモや質疑応答は &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2026"&gt;PyCon mini Shizuoka 2026 - 清水川のScrapbox&lt;/a&gt; にメモしました。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id10&gt;
&lt;h2&gt;ブース出展&lt;/h2&gt;
&lt;p&gt;Flying Duck 社で副業を1年ほどしてます（いずれblog書きたい）。
代表の八木さんは今回イベントの当日スタッフもやっているため、ブースにずっと居るわけにもいかず、午後は私がお店番しつつトークを聞いたり、ブースに来てくれた方何人かと話したりしていました。&lt;/p&gt;
&lt;figure class=align-default id=id21&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/flyingduck-booths.jpg"&gt;&lt;img alt="../../../../_images/flyingduck-booths.jpg" src="https://www.freia.jp/taka/_images/flyingduck-booths.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Flying Duck ブースの、用意したロゴ入りテーブルクロスが眩しい&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;14:50 からのブース出展ショートトークでは、kata-studio さん、Flying Duck、さくらインターネット、PythonED、BeProud などが、5分LT形式でスポンサートークを行いました。&lt;/p&gt;
&lt;figure class=align-default id=id22&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/flyingduck-talk.jpg"&gt;&lt;img alt="../../../../_images/flyingduck-talk.jpg" src="https://www.freia.jp/taka/_images/flyingduck-talk.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Flying Duck のスポンサートーク（横に立ってみた）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;&lt;a class="reference external" href="https://docs.google.com/presentation/d/e/2PACX-1vTvvT_6IQpW23Z7CWk76cMAVCxL1Wcm0jqMjzEivQkTzAjzfcpuQQxmQI-8PmpZarnYfZsM200qVgXb/pub"&gt;Flying DuckのLTスライド&lt;/a&gt; は前日に八木さんが作ったものを私と会社のもう1人とでレビューをして、話す順番を入れ替えたり、トーンを調整したりして用意しました。Flying Duckのシステムは、グリーンエナジーを活用して工場の電力需要と燃料消費を社会全体で最適化することを目指しています、という話をPythonのカンファレンスで分かりやすく、面白く伝えるには話をどう展開したら良いか・・・、試行錯誤した甲斐あって会場の反応も良かったように思います。&lt;/p&gt;
&lt;iframe allowfullscreen=true frameborder=0 height=299 mozallowfullscreen=true src="https://docs.google.com/presentation/d/e/2PACX-1vTvvT_6IQpW23Z7CWk76cMAVCxL1Wcm0jqMjzEivQkTzAjzfcpuQQxmQI-8PmpZarnYfZsM200qVgXb/pubembed?start=false&amp;amp;loop=false&amp;amp;delayms=3000" webkitallowfullscreen=true width=480&gt;&lt;/iframe&gt;&lt;p&gt;そういえば、ブースで銭湯経営で重油消費をなんとか改善したいという方の話を聞くこともでき、大規模工場でなくてもニーズがありそうな予感がしました。&lt;/p&gt;
&lt;p&gt;LTについて詳しくは &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2026"&gt;PyCon mini Shizuoka 2026 - 清水川のScrapbox&lt;/a&gt; にメモしました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=lt&gt;
&lt;h2&gt;LT &amp;amp; クロージング&lt;/h2&gt;
&lt;p&gt;17:20 から LT &amp;amp; クロージング。&lt;/p&gt;
&lt;figure class=align-default id=id23&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lt.jpg"&gt;&lt;img alt="../../../../_images/lt.jpg" src="https://www.freia.jp/taka/_images/lt.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;LTのwhitphxさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;LTでは、Yuichiro Tachibana (whitphx) さんの話 &lt;a class="reference external" href="https://slides.whitphx.info/202602-oss-give-and-take/"&gt;How OSS becomes a give-and-take activity&lt;/a&gt; が良かった。
「OSSへの貢献は &lt;strong&gt;善意&lt;/strong&gt; だけでなく、保守コストを減らしてお互いを活かす &lt;strong&gt;経済合理性&lt;/strong&gt; で持続する」という内容でした。
20年以上OSSに関わってきたなかで、OSSコードにカスタマイズパッチを当てて使い続けるのが大変だ、という企業利用者の話は何度も聞いたことがあります。OSSへの寄生ではなく共生関係を作れた例としてとても良い事例の紹介でした。&lt;/p&gt;
&lt;p&gt;そしてクロージング。&lt;/p&gt;
&lt;figure class=align-default id=id24&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/closing3.jpg"&gt;&lt;img alt="../../../../_images/closing3.jpg" src="https://www.freia.jp/taka/_images/closing3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;クロージング&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;最後にみんなで集合写真を撮影して、解散になりました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id11&gt;
&lt;h2&gt;公式パーティー&lt;/h2&gt;
&lt;p&gt;18:20 から会場内でパーティーが行われました。去年はお店へ移動しましたが、今年は会場そのままでの開催。会場移動なしだと、イベント参加そのままの雰囲気で色々な人と話せて良いですね。あと、立食だと適度にまざりつつ話せるのでそれも良い。&lt;/p&gt;
&lt;p&gt;パーティー冒頭で、West Coast Brewing の樽がサプライズ登場！すごい！
（一部のビール好きのひとたちがキャッキャしてました。キャッキャッ）
わざわざ用宗まで車で取りに行ってきてくれたとのこと。塚本さんありがと～！&lt;/p&gt;
&lt;figure class=align-default id=id25&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party-kyakkya.gif"&gt;&lt;img alt="../../../../_images/party-kyakkya.gif" src="https://www.freia.jp/taka/_images/party-kyakkya.gif" style="height: 400px;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;キャッキャッ&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;ビールは他にもWCBの500ml缶や御殿場高原ビールの1L缶などあり、また、料理のオードブルもかなり美味しかった！&lt;/p&gt;
&lt;figure class=align-default id=id26&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party-food.jpg"&gt;&lt;img alt="../../../../_images/party-food.jpg" src="https://www.freia.jp/taka/_images/party-food.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オードブル美味しかった&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id27&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party-kanpai.jpg"&gt;&lt;img alt="../../../../_images/party-kanpai.jpg" src="https://www.freia.jp/taka/_images/party-kanpai.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;かんぱい！&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id28&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party-beers.jpg"&gt;&lt;img alt="../../../../_images/party-beers.jpg" src="https://www.freia.jp/taka/_images/party-beers.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ありがとうございました！&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id12&gt;
&lt;h2&gt;感想&lt;/h2&gt;
&lt;p&gt;去年はキーノートとして参加したこともあり前夜まで準備が大変でしたが、今年は登壇なしでスポンサー関係者、という少し違う角度からイベントを楽しめました。&lt;/p&gt;
&lt;p&gt;イベント運営のみなさん、素敵なイベント開催、ありがとうございました！&lt;/p&gt;
&lt;p&gt;次は、3月にフィリピンで開催される PythonAsia イベント（ &lt;a class="reference external" href="https://www.freia.jp/taka/blog/2026/02/pyconshizuoka2026/TBD"&gt;PyCon APACの後継のようなもの&lt;/a&gt; ）に行きます。トーク予定あり。
この1年、英語の練習は続けていますが、トーク練習はあんちょこを見ずに英語で話せるように準備しないと.. がんばろう。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Mon, 23 Feb 2026 23:59:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2026/02/pyconshizuoka2026/index.html</guid></item><item><title>Pyxelで作るレトロプレゼンスライド</title><link>https://www.freia.jp/taka/blog/2025/12/pyxel-slide/index.html</link><description>&lt;section id=pyxel&gt;

&lt;section id=id1&gt;
&lt;h2&gt;はじめに&lt;/h2&gt;
&lt;p&gt;Pyxel版での表示をご利用ください。&lt;/p&gt;
&lt;figure class=align-default id=id14&gt;
&lt;a class="reference external image-reference" href="https://shimizukawa.github.io/pyxel-slide-2025/"&gt;&lt;img alt="../../../../_images/slide-pyxel.png" src="https://www.freia.jp/taka/_images/slide-pyxel.png"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Pyxelで作るレトロプレゼンスライド、で作ったスライド &lt;br&gt;
&lt;a class="reference external" href="https://shimizukawa.github.io/pyxel-slide-2025/"&gt;https://shimizukawa.github.io/pyxel-slide-2025/&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;同じ内容の Sphinx-revealjs 版スライドもあります。&lt;/p&gt;
&lt;figure class=align-default id=id15&gt;
&lt;a class="reference external image-reference" href="https://shimizukawa.github.io/pyxel-slide-2025/revealjs/slide-ja.html"&gt;&lt;img alt="../../../../_images/slide-revealjs.png" src="https://www.freia.jp/taka/_images/slide-revealjs.png"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Pyxelで作るレトロプレゼンスライド、のSphinx-revealjsビルド版 &lt;br&gt;
&lt;a class="reference external" href="https://shimizukawa.github.io/pyxel-slide-2025/revealjs/slide-ja.html"&gt;https://shimizukawa.github.io/pyxel-slide-2025/revealjs/slide-ja.html&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;section id=id2&gt;
&lt;h3&gt;この記事/スライドは？&lt;/h3&gt;
&lt;p&gt;この記事はPythonでレトロゲームが作れる「&lt;a class="reference external" href="https://github.com/kitao/pyxel"&gt;Pyxel&lt;/a&gt;」のアドベントカレンダー、「&lt;a class="reference external" href="https://qiita.com/advent-calendar/2025/pyxel"&gt;Pyxel Advent Calendar 2025&lt;/a&gt;」の16日目の記事です。
よろしくお願いします。&lt;/p&gt;
&lt;p&gt;書いた人: @shimizukawa です。&lt;/p&gt;
&lt;figure class=align-default&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/face-dot.png"&gt;&lt;img alt="../../../../_images/face-dot.png" src="https://www.freia.jp/taka/_images/face-dot.png" style="width: 32.0px; height: 24.0px;"&gt;
&lt;/a&gt;
&lt;/figure&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;1990年頃にゲームを作りたくてプログラミングを始めました&lt;/li&gt;
&lt;li&gt;&lt;p&gt;当時はC言語、ASM、DirectXとハードルが高くて未完ばかりでした&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pyxelで、あの頃作りたかったゲーム作りに再挑戦中です&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id3&gt;
&lt;h3&gt;レトロプレゼンスライド、って何？&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;レトロプレゼンスライド&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;レトロゲームエンジンで動作する、プレゼンテーションスライド表示アプリケーションです。&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;作ったきっかけ&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html"&gt;あるイベント&lt;/a&gt;で「1990年頃に作りたかったゲームをPyxelで作った」というプレゼンをしました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スライドを作りながら、それならプレゼンスライド自体もPyxelで作ったら面白いのでは、と思って作りました。&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;この記事では、その実装方法を紹介します。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;レトロプレゼンスライドのPyxel要素&lt;/h2&gt;
&lt;p&gt;Pixel関連の技術要素を紹介します。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;日本語文字表示&lt;/li&gt;
&lt;li&gt;&lt;p&gt;画像バンク&lt;/li&gt;
&lt;li&gt;&lt;p&gt;画像埋め込み表示&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ディザリングによるページ切替アニメーション&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pyxelアプリをスライド内に埋め込み&lt;/li&gt;
&lt;/ul&gt;
&lt;section id=id5&gt;
&lt;h3&gt;日本語文字表示&lt;/h3&gt;
&lt;p&gt;日本語BDFフォント（Bitmap Distribution Format）を使いました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;テキストで定義された、文字コードに対応したビットマップ情報&lt;/li&gt;
&lt;li&gt;&lt;p&gt;採用 &lt;a class="reference external" href="http://openlab.ring.gr.jp/efont/unicode/"&gt;http://openlab.ring.gr.jp/efont/unicode/&lt;/a&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;日本語をUnicodeで扱えて、大きい文字サイズが用意されている&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;不採用: TrueTypeフォントからBDFに変換するツール&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;配布とライセンスの問題を避けたかったため&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=n&gt;font_title&lt;/span&gt;     &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Font&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/b24.bdf"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;font_pagetitle&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Font&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/b16_b.bdf"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;font_default&lt;/span&gt;   &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Font&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/b12.bdf"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;font_bold&lt;/span&gt;      &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Font&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/b12_b.bdf"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;font_italic&lt;/span&gt;    &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Font&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/b12_i.bdf"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id=id6&gt;
&lt;h3&gt;画像バンク&lt;/h3&gt;
&lt;p&gt;独自の画像バンクを複数使って競合を避けています。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;Pyxelの画像バンクを2つ使って、スライド切替アニメーション&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スライド進捗に合わせたキャラクター描画用画像バンク&lt;/li&gt;
&lt;li&gt;&lt;p&gt;さらに、別の画像バンクに子アプリを描画してオーバーレイ&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=n&gt;renderd_page_bank&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=p&gt;[&lt;/span&gt;
    &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Image&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;WIDTH&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;HEIGHT&lt;/span&gt;&lt;span class=p&gt;),&lt;/span&gt;
    &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Image&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;WIDTH&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;HEIGHT&lt;/span&gt;&lt;span class=p&gt;),&lt;/span&gt;
&lt;span class=p&gt;]&lt;/span&gt;
&lt;span class=n&gt;player_image&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Image&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;from_image&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"assets/urban_rpg.png"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;section id=dither&gt;
&lt;h3&gt;ditherによるページ切替アニメーション&lt;/h3&gt;
&lt;p&gt;Pyxelの &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;dither&lt;/span&gt;&lt;/code&gt; 関数を使って、2つのスライドを合成しながら入れ替え&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=n&gt;new_img&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;get_rendered_img&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;page&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;old_img&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;get_rendered_img&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;old_page&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=c1&gt;# old&lt;/span&gt;
&lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;dither&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;rate&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;blt&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;old_x&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;old_y&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;old_img&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;WIDTH&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;HEIGHT&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;7&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=c1&gt;# new&lt;/span&gt;
&lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;dither&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=mi&gt;1&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt; &lt;span class=n&gt;rate&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;blt&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;new_x&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;new_y&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;new_img&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;WIDTH&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;HEIGHT&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;7&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;dither&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=mi&gt;1&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;こんな感じで動きます。&lt;/p&gt;
&lt;figure class=align-default id=id16&gt;
&lt;video controls src="../../../../_images/pyxel-slide-dither.mp4" title="../../../../_images/pyxel-slide-dither.mp4"&gt;
&lt;a href="https://www.freia.jp/taka/_images/pyxel-slide-dither.mp4"&gt;../../../../_images/pyxel-slide-dither.mp4&lt;/a&gt;
&lt;/video&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Pyxelのdither関数を使ったスライド切替アニメーション&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=pyxel-1-2&gt;
&lt;h3&gt;Pyxelアプリをスライド内に埋め込み 1/2&lt;/h3&gt;
&lt;p&gt;マウスを子アプリにフォーカスして、子アプリに制御を渡します。&lt;/p&gt;
&lt;figure class=align-default&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/typinggame.png"&gt;&lt;img alt="../../../../_images/typinggame.png" src="https://www.freia.jp/taka/_images/typinggame.png" style="width: 300.0px; height: 165.0px;"&gt;
&lt;/a&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=pyxel-2-2&gt;
&lt;h3&gt;Pyxelアプリをスライド内に埋め込み 2/2&lt;/h3&gt;
&lt;p&gt;子アプリは画像バンクに書き込み、スライドにオーバーレイしてます。&lt;/p&gt;
&lt;figure class=align-default&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jumpman.png"&gt;&lt;img alt="../../../../_images/jumpman.png" src="https://www.freia.jp/taka/_images/jumpman.png" style="width: 374.0px; height: 272.0px;"&gt;
&lt;/a&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id7&gt;
&lt;h2&gt;レトロプレゼンスライドのスライド要素&lt;/h2&gt;
&lt;p&gt;スライド関連の技術要素を紹介します。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;参考: Markdownスライドレンダラー&lt;/li&gt;
&lt;li&gt;&lt;p&gt;技術スタック&lt;/li&gt;
&lt;li&gt;&lt;p&gt;アーキテクチャ&lt;/li&gt;
&lt;li&gt;&lt;p&gt;レイアウト、表現、動作&lt;/li&gt;
&lt;li&gt;&lt;p&gt;コードフェンス（+ハイライト）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;画像表示&lt;/li&gt;
&lt;/ul&gt;
&lt;section id=markdown&gt;
&lt;h3&gt;参考: Markdownスライドレンダラー&lt;/h3&gt;
&lt;p&gt;スライド作りにMarkdown記法を使うと便利です。
レイアウトに悩まされず、公開や再利用も楽になります。&lt;/p&gt;
&lt;p&gt;MarkdownをHTMLスライドに変換するツールはいくつかあります。
これらはレンダラーにHTMLを使っています。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://sli.dev/"&gt;Slidev&lt;/a&gt; : Vue.jsベースのスライド作成ツール&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://remarkjs.com/"&gt;Remark.js&lt;/a&gt; : ブラウザ上でMarkdownスライドをレンダリング&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://revealjs.com/"&gt;Reveal.js&lt;/a&gt; : HTMLスライドフレームワーク&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.sphinx-doc.org/ja/master/"&gt;Sphinx&lt;/a&gt; に組み込む &lt;a class="reference external" href="https://sphinx-revealjs.readthedocs.io/"&gt;sphinx-revealjs&lt;/a&gt; 拡張&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;今回は、こういったツールを参考に、Pyxelで実装しました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id8&gt;
&lt;h3&gt;技術スタック&lt;/h3&gt;
&lt;p&gt;利用ライブラリ&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;markdown-it-py&lt;/span&gt;&lt;/code&gt;: Markdownパーサー&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;pygments&lt;/span&gt;&lt;/code&gt;: コードハイライト&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;実装、記法、動作仕様は、以下を参考にしました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;myst-parser&lt;/span&gt;&lt;/code&gt;: Markdown記法の拡張&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;sphinx-revealjs&lt;/span&gt;&lt;/code&gt;: SphinxのReveal.js拡張&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id9&gt;
&lt;h3&gt;アーキテクチャ&lt;/h3&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;読み込み&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;markdownit-py&lt;/span&gt;&lt;/code&gt; でMarkdownをトークンに分割&lt;/li&gt;
&lt;li&gt;&lt;p&gt;木構造のトークンをスライド単位で保持&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;描画&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;見ているページをVisitorパターンでレンダリング&lt;/li&gt;
&lt;li&gt;&lt;p&gt;記法に合わせて文字をレイアウト&lt;/li&gt;
&lt;li&gt;&lt;p&gt;2枚のバンクでスライドめくりアニメーション&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;操作&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;キーボード、マウス、パッドでページ移動&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Ctrl+R でMarkdownを再読み込み&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id=id10&gt;
&lt;h3&gt;レイアウト、表現、動作&lt;/h3&gt;
&lt;p&gt;対応している記法&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;ヘディング1,2,3 = スライド,セクション,ページタイトル&lt;/li&gt;
&lt;li&gt;&lt;p&gt;番号なし,番号つき箇条書き&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;strong&gt;強調&lt;/strong&gt;, &lt;em&gt;斜体&lt;/em&gt;,  &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;literal&lt;/span&gt;&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;URL link: &lt;a class="reference external" href="https://example.com"&gt;https://example.com&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;コードフェンス（+ハイライト）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;画像読み込み ( &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;{figure}&lt;/span&gt; &lt;span class=pre&gt;file.png&lt;/span&gt;&lt;/code&gt; )&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pyxel App 読み込み ( &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;{figure}&lt;/span&gt; &lt;span class=pre&gt;file.py&lt;/span&gt;&lt;/code&gt; )&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;（HTMLのレイアウトエンジンは良く出来てるなあ...）&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id11&gt;
&lt;h3&gt;コードフェンス（+ハイライト）&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;pygments&lt;/span&gt;&lt;/code&gt; の &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;RawTokenFormatter&lt;/span&gt;&lt;/code&gt; でtokenize&lt;/li&gt;
&lt;li&gt;&lt;p&gt;リスト構造のTokenを for match case で順次レンダリング&lt;/p&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=n&gt;hl&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pygments&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;highlight&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;content&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;lexer&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;formatter&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=k&gt;for&lt;/span&gt; &lt;span class=n&gt;line&lt;/span&gt; &lt;span class=ow&gt;in&lt;/span&gt; &lt;span class=n&gt;hl&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;decode&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"utf-8"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;splitlines&lt;/span&gt;&lt;span class=p&gt;():&lt;/span&gt;
    &lt;span class=n&gt;token&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;value&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;line&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;split&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"&lt;/span&gt;&lt;span class=se&gt;\t&lt;/span&gt;&lt;span class=s2&gt;"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
    &lt;span class=k&gt;match&lt;/span&gt; &lt;span class=n&gt;token&lt;/span&gt;&lt;span class=p&gt;:&lt;/span&gt;
        &lt;span class=k&gt;case&lt;/span&gt; &lt;span class=s2&gt;"Token.Operator.Word"&lt;/span&gt;&lt;span class=p&gt;:&lt;/span&gt;
            &lt;span class=k&gt;with&lt;/span&gt; &lt;span class=n&gt;with_color&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;2&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt;&lt;span class=mi&gt;1&lt;/span&gt;&lt;span class=p&gt;):&lt;/span&gt;
                &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;_text&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;value&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
        &lt;span class=o&gt;...&lt;/span&gt;
        &lt;span class=k&gt;case&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=k&gt;_&lt;/span&gt;&lt;span class=p&gt;:&lt;/span&gt;
            &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;_text&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;value&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id12&gt;
&lt;h3&gt;画像埋め込み表示&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;pyxel.Image.from_image&lt;/span&gt;&lt;/code&gt; で画像を読み込み&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ただし画面解像度が低いので、大きな画像は潰れてしまう&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight-python notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=n&gt;p&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=n&gt;pyxel&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;Image&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;from_image&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;filename&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=n&gt;x&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;y&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;w&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;h&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;x&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;y&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;p&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;width&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;p&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;height&lt;/span&gt;
&lt;span class=n&gt;s&lt;/span&gt; &lt;span class=o&gt;=&lt;/span&gt; &lt;span class=mf&gt;0.5&lt;/span&gt;
&lt;span class=bp&gt;self&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;img&lt;/span&gt;&lt;span class=o&gt;.&lt;/span&gt;&lt;span class=n&gt;blt&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;
    &lt;span class=n&gt;x&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt; &lt;span class=nb&gt;int&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;w&lt;/span&gt; &lt;span class=o&gt;*&lt;/span&gt; &lt;span class=p&gt;(&lt;/span&gt;&lt;span class=mi&gt;1&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt; &lt;span class=n&gt;s&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt; &lt;span class=o&gt;/&lt;/span&gt; &lt;span class=mi&gt;2&lt;/span&gt;&lt;span class=p&gt;),&lt;/span&gt;
    &lt;span class=n&gt;y&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt; &lt;span class=nb&gt;int&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=n&gt;h&lt;/span&gt; &lt;span class=o&gt;*&lt;/span&gt; &lt;span class=p&gt;(&lt;/span&gt;&lt;span class=mi&gt;1&lt;/span&gt; &lt;span class=o&gt;-&lt;/span&gt; &lt;span class=n&gt;s&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt; &lt;span class=o&gt;/&lt;/span&gt; &lt;span class=mi&gt;2&lt;/span&gt;&lt;span class=p&gt;),&lt;/span&gt;
    &lt;span class=n&gt;p&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
    &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=mi&gt;0&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;w&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt; &lt;span class=n&gt;h&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
    &lt;span class=n&gt;scale&lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=n&gt;s&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=p&gt;)&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id13&gt;
&lt;h2&gt;おわりに&lt;/h2&gt;
&lt;p&gt;なぜか、今日もゲーム作りが進みません！&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;Pyxelでレトロ調プレゼンスライドを作りました&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Markdown記法でスライドを作成できます&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pyxelで作ったゲームを埋め込んでプレゼンできます&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ソースコードは以下のリポジトリにあります&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://github.com/shimizukawa/pyxel-slide-2025"&gt;https://github.com/shimizukawa/pyxel-slide-2025&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Tue, 16 Dec 2025 01:00:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/12/pyxel-slide/index.html</guid></item><item><title>PyCon mini 東海 2025 に参加しました</title><link>https://www.freia.jp/taka/blog/2025/11/pycontokai2025/index.html</link><description>&lt;section id=pycon-mini-2025&gt;

&lt;p&gt;11月08日（土）に、名古屋で開催された、PyCon mini 東海 2025に参加しました。
&lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2024/11/pycontokai2024/index.html"&gt;&lt;span class=doc&gt;昨年&lt;/span&gt;&lt;/a&gt; の初開催に続けて、2回目の開催です。&lt;/p&gt;
&lt;figure class=align-default id=id21&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/opening02.jpg"&gt;&lt;img alt="../../../../_images/opening02.jpg" src="https://www.freia.jp/taka/_images/opening02.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;PyCon mini 東海 2025 ！&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;参加人数はconnpass上で50名（スタッフ等入れて60名前後）で当日LTありと、「昨年よりちょっとパワーアップ（by 座長）」でした。&lt;/p&gt;
&lt;p&gt;トラック数は1つでキーノートを含むトーク8個、トラック2でワークショップ3個、と昨年と同様の構成でした。
ワークショップを覗きに行くのを忘れてしまいましたが、ある回は10人くらい参加者がいて賑わっていたようです。&lt;/p&gt;
&lt;p&gt;そして、ランチも名古屋めし弁当が2種にパワーアップ、無限コーヒーあり（有限）の、相変わらずminiと言うには頑張りすぎている気もする盛りだくさんなイベントだったと思います。&lt;/p&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon mini 東海 2025&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/"&gt;https://tokai.pycon.jp/2025/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;2025年11月08日（土）&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;名古屋市中区栄 中日ホール&amp;amp;カンファレンス&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;参加費&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;パトロン10000円、一般3000円、学生1000円&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;私の参加時のメモ（blog元ネタ）が &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_%E6%9D%B1%E6%B5%B7_2025"&gt;PyCon mini 東海 2025 - 清水川のScrapbox&lt;/a&gt; にあります。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id2&gt;
&lt;h2&gt;開場～オープニング&lt;/h2&gt;
&lt;p&gt;1年ぶり2回目の名古屋駅 → 栄駅 → 中日ホール&amp;amp;カンファレンス（会場）ルートは迷わず移動できました。一番迷いそうになったのは名古屋で新幹線口をでてから東山線に乗り換えるところだったかもしれない。来年はもうナビなしで移動できそうです。&lt;/p&gt;
&lt;figure class=align-default id=id22&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/reception3.jpg"&gt;&lt;img alt="../../../../_images/reception3.jpg" src="https://www.freia.jp/taka/_images/reception3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;受付の様子&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;10時からオープニング開始。座長のりょうさんから「昨年よりちょっとパワーアップ」という紹介がありました。&lt;/p&gt;
&lt;figure class=align-default id=id23&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/opening11.png"&gt;&lt;img alt="../../../../_images/opening11.png" src="https://www.freia.jp/taka/_images/opening11.png" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニングトーク&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id3&gt;
&lt;h2&gt;キーノート&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;10:30 ~ 11:20&lt;/li&gt;
&lt;li&gt;&lt;p&gt;村橋 究理基&lt;/li&gt;
&lt;li&gt;&lt;p&gt;教育・研究現場で活用されるPython&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-keynote"&gt;https://tokai.pycon.jp/2025/#session-keynote&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.ep.sci.hokudai.ac.jp/~mkuriki/study/PyCon-mini-tokai-2025-mkuriki.pdf"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default id=id24&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/keynote2.jpg"&gt;&lt;img alt="../../../../_images/keynote2.jpg" src="https://www.freia.jp/taka/_images/keynote2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;キーノートの村橋さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;村橋 究理基さんのキーノートは、語り口が軽快で面白かった。「タイトルが固い」という自虐から始まり、開始15分でRubyの話を経てやっとPythonの話になるという展開。ご本人も、序盤Rubyの話をずっとしてる的なことを言いながら、Ruby松江シールを配ってました。&lt;/p&gt;
&lt;figure class=align-default id=id25&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/keynote-ruby.jpg"&gt;&lt;img alt="../../../../_images/keynote-ruby.jpg" src="https://www.freia.jp/taka/_images/keynote-ruby.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Ruby City MATSUE シール&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;島根大学での話が中心で、RaspberryPiでコマ撮りした写真をタイムラプス動画にしてYouTubeに上げているプロジェクトの紹介がありました（ &lt;a class="reference external" href="https://www.youtube.com/watch?v=Mjd5fyQaQ0w"&gt;[2025/11/06] タイムラプス 北海道大学から札幌駅方向 - YouTube&lt;/a&gt; ）。トーク全体は、主言語にPythonを使っているとか、講義や演習でPythonを教えているとかに関係なく、Pythonが色々な人に色々なところで使われていている言語だという現状でどう付き合っていっているか、ということの紹介だったと思います。&lt;/p&gt;
&lt;p&gt;質疑応答では、島根大学でのPython教育について質問が出ました。公式には各学科でPythonを教えていることにはなっていないけれど、解析にはmatplotlibなどが必要で独学で学んでいるし、教員も教えているとのこと。Ruby振興に松江市がお金を出しているという大人の事情もあるそうですが、C/C++はしっかり教えて、それゆえPythonを独学で学べる程度の基礎力を付けているので、あとは独学できるという話でした。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h2&gt;トークセッション（午前）&lt;/h2&gt;
&lt;section id=pyscriptopencvwebai&gt;
&lt;h3&gt;PyScriptとOpenCVを使ってWebで画像処理AI&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;11:35 ~&lt;/li&gt;
&lt;li&gt;&lt;p&gt;高橋 かずひと&lt;/li&gt;
&lt;li&gt;&lt;p&gt;PyScriptとOpenCVを使ってWebで画像処理AI&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-1"&gt;https://tokai.pycon.jp/2025/#session-talk-1&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://kazuhito00.github.io/Pycon-mini-Tokai-2025-PyScript-OpenCV/index.html"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;高橋 かずひとさんのトークは、PyScriptの実践的な活用例でした。&lt;/p&gt;
&lt;figure class=align-default id=id26&gt;
&lt;img alt="../../../../_images/talk1.jpg" src="https://www.freia.jp/taka/_images/talk1.jpg"&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;高橋 かずひとさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;PyScriptでは、NumPy、OpenCV、Pillowが使えて、TensorFlowやPyTorchの代わりにOpenCV DNNを使うことでAI画像処理が実現できるとのこと。そして、PyScriptでメディアデバイス（Webカメラ）にアクセスしてオンデマンドで物体検知するデモで会場から良い反応がありました。インストール無しでここまで出来るのはすごい。&lt;/p&gt;
&lt;p&gt;デモではYOLOを使った物体検出を見せてくれましたが、推論自体はそんなに遅くないけどCanvas反映が遅いという課題があるそうです。create_proxy を使うと速いけどメモリリークがあったので今回は避けたとのこと。&lt;/p&gt;
&lt;p&gt;今回のスライドは全てGitHub Pagesで動作しているというのも面白いポイントでした。
そういえば昨年のPyCon mini 東海2024では、めっちゃ動くPowerPointスライドで会場を沸かせてたなあ。&lt;/p&gt;
&lt;p&gt;質疑応答では、「Python処理系のWASM/WASI対応について」 （@aodag）、「PyOdideとPyScriptの違いについて」（@nikkie）、「OpenCV DNN も学習済みモデルを取り込めるのか？」（@terapyon）といった質問がありました。PyScriptの推しポイントは「Pythonそのままのソースコードをアップロードできる」ことと「PyOdideのラッパーとして使いやすくしている」ことだそうです。そして、他のTensorFlow等で作ったモデルをそのままOpenCV DNNで使えるが、これはまだ開発中で最新のモデルが使えないなどの制限がある、ということでした。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=ai&gt;
&lt;h3&gt;個人ではじめるマルチAIエージェント入門&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;12:05 ～ 12:30&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Tomoko FURUKI (@komo_fr)&lt;/li&gt;
&lt;li&gt;&lt;p&gt;個人ではじめるマルチAIエージェント入門 〜LangChain × LangGraphでアイデアを形にするステップ〜&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-2"&gt;https://tokai.pycon.jp/2025/#session-talk-2&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://speakerdeck.com/komofr/pycon-mini-tokai"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;@komo_fr さんのトークは、 &lt;a class="reference external" href="https://pypi.org/project/langchain/"&gt;LangChain&lt;/a&gt; × &lt;a class="reference external" href="https://pypi.org/project/langgraph/"&gt;LangGraph&lt;/a&gt; を使ったマルチAIエージェントの実装でした。インプットに対して複数のAI処理を行って結果を出す、その微調整の試行錯誤をめっちゃ楽にするためのフレームワーク群の紹介です。&lt;/p&gt;
&lt;p&gt;児童文学サークル出身で、文学を小学校低学年向けに変換するAIエージェントを作ったときに使ったツールチェインを紹介するというものでした。マルチエージェントのお手本っぽいチャートもあり、分かりやすく、見ていてとても面白かったです。&lt;/p&gt;
&lt;figure class=align-default id=id27&gt;
&lt;img alt="../../../../_images/talk2.jpg" src="https://www.freia.jp/taka/_images/talk2.jpg"&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;&lt;a class="reference external" href="https://pypi.org/project/langgraph/"&gt;LangGraph&lt;/a&gt; を紹介する @komo_fr さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;楽に開発できるようにする工夫として、まずJSONを直に扱うと補完も効かず手間が多かったため、 &lt;a class="reference external" href="https://pypi.org/project/pydantic/"&gt;Pydantic&lt;/a&gt; でデータ構造を定義してstructured outputsを利用するようにしたとのこと。さらに &lt;a class="reference external" href="https://pypi.org/project/langgraph/"&gt;LangGraph&lt;/a&gt; を導入して、エージェントのワークフローをグラフ構造で定義し、各エージェントが扱うデータをステートとして受け渡せるようにすることで、処理の流れがかなり見通しよくなっていました。 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;graph.get_graph.draw_mermaid_png()&lt;/span&gt;&lt;/code&gt; でワークフローグラフを Mermaid 形式で出力できるのも便利そう。&lt;/p&gt;
&lt;p&gt;（JSONだと型定義が活用できないので、スループットとのトレードオフはあるらしいですが良い選択だなと思いました。あと余談ですが、MCPサーバーの &lt;a class="reference external" href="https://modelcontextprotocol.io/specification/2025-06-18/server/tools#structured-content"&gt;Structured Content&lt;/a&gt; をPydanticで実装したのを思いだしました）&lt;/p&gt;
&lt;p&gt;また、 &lt;a class="reference external" href="https://pypi.org/project/langchain/"&gt;LangChain&lt;/a&gt; 開発元が提供する &lt;a class="reference external" href="https://pypi.org/project/langsmith/"&gt;LangSmith&lt;/a&gt; を使って、実行ログを Web ダッシュボード上で評価、管理していました。 &lt;a class="reference external" href="https://pypi.org/project/langgraph/"&gt;LangGraph&lt;/a&gt; の実行結果を人間が評価してコンソールからスコアを入力し、その評価を &lt;a class="reference external" href="https://pypi.org/project/langsmith/"&gt;LangSmith&lt;/a&gt; に送ることでエージェントの振る舞いを改善していける、という話が、「実務で使う」感があって良かったです。&lt;/p&gt;
&lt;p&gt;エージェントの質を上げる工夫として、作品でよく言及される名言や印象的なフレーズを &lt;a class="reference external" href="https://docs.langchain.com/oss/python/integrations/retrievers/tavily"&gt;TavilySearchAPIRetriever&lt;/a&gt; で Web から取得し、それを sentence-transformers によるコサイン類似度検索で原文から正確に拾ってくる、という流れを紹介していました。さらに、同じ作者の別作品の文体を模倣する「文体模倣エージェント」を追加して、子ども向けに書き換えても元の作品の雰囲気を維持できるようにしているのが印象的でした。&lt;/p&gt;
&lt;p&gt;質疑応答では、「一番苦労したのは（スライドには書いていない）文体の部分」という話や、LLM のバージョン比較の話（ChatGPT-4.1, 4.5, 5 で比較したところ 4.5 が一番良かった、5 は短文になりがちだった）という裏話が面白かった。このあたりの泥臭い部分は、実際にやってみると難しくて、簡単には乗り越えられないだろうなあ。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id8&gt;
&lt;h2&gt;ランチタイム&lt;/h2&gt;
&lt;p&gt;12:30 - 13:50&lt;/p&gt;
&lt;p&gt;今回はお弁当が2種類！
尾張御膳（おわりごぜん）と十二単（じゅうにひとえ）でした。&lt;/p&gt;
&lt;figure class=align-default id=id28&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/bento1.jpg"&gt;&lt;img alt="../../../../_images/bento1.jpg" src="https://www.freia.jp/taka/_images/bento1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;十二単&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id29&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/bento2.jpg"&gt;&lt;img alt="../../../../_images/bento2.jpg" src="https://www.freia.jp/taka/_images/bento2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;尾張御膳（フードロス対策で2つめを頂きました）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;スクリーン前にコミュニケーションエリアが用意されていて、初めて会った人同士で話しやすい環境作りがされていました。&lt;/p&gt;
&lt;figure class=align-default id=id30&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lunch-talks.jpg"&gt;&lt;img alt="../../../../_images/lunch-talks.jpg" src="https://www.freia.jp/taka/_images/lunch-talks.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ランチの様子&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id9&gt;
&lt;h2&gt;トークセッション（午後）&lt;/h2&gt;
&lt;section id=python&gt;
&lt;h3&gt;Pythonでやってはいけないやってみるべきこと&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;13:50 -14:15&lt;/li&gt;
&lt;li&gt;&lt;p&gt;@aodag&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pythonでやってはいけないやってみるべきこと&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-3"&gt;https://tokai.pycon.jp/2025/#session-talk-3&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://github.com/aodag/pyconmini-tokai-2025"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;@aodagさんのトークは、昼ご飯の後のまったりとした時間に技術の話をしますよ、という前置きから始まる、語り口が超おもしろいセッションでした。&lt;/p&gt;
&lt;figure class=align-default id=id31&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk3.jpg"&gt;&lt;img alt="../../../../_images/talk3.jpg" src="https://www.freia.jp/taka/_images/talk3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@aodagさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;前半は、最近の mypy や ruff、pyright など静的解析ツールが充実してきた流れに対して「Pythonってダイナミックな言語なはずなのに静的型チェックとかなんなんだよ！」という、モダンPythonの「安全で窮屈」さの話。たしかに、ちょっとした雑なスクリプトがIDEで警告されるのは私も時々邪魔だなあと思ったりします。そこから「冒険的プログラミング」として、「あえて悪いことをしてみよう」「違う自分になってみよう」として &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;cat.__class__&lt;/span&gt; &lt;span class=pre&gt;=&lt;/span&gt; &lt;span class=pre&gt;Dog&lt;/span&gt;&lt;/code&gt; で &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;cat.greet()&lt;/span&gt;  &lt;span class=pre&gt;#&lt;/span&gt; &lt;span class=pre&gt;=&amp;gt;&lt;/span&gt; &lt;span class=pre&gt;わん&lt;/span&gt;&lt;/code&gt; になるコードを紹介。それでも「いくらやっても（壊そうとしても）、Pythonの手のひらから出られない、Pythonの手のひらってどこだよ」とか、漫談を目指したというトークはしっかり面白かった。さすがだなあ。&lt;/p&gt;
&lt;p&gt;まとめとして挙げられていた「やってみるべきこと」は、&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;ふとした疑問を試してみる&lt;/li&gt;
&lt;li&gt;&lt;p&gt;さらに疑問を投げかける&lt;/li&gt;
&lt;li&gt;&lt;p&gt;黒魔術との境に気をつける&lt;/li&gt;
&lt;li&gt;&lt;p&gt;黒魔術に気付く&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;質疑応答では、「仕事でやらかしちゃった事ってありますか？」という率直な質問に対して、「存分に……本番のOracleのセッションをロックしたことがあります」とさらっと答えていました。また、&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;__class__&lt;/span&gt;&lt;/code&gt; の差し替えは仕様として禁止した方がいいのでは？という質問に「禁止して良いと思う」「Zopeの人たちはなんとかすると思うので良いと思います」という返しもあり、現実世界とのバランス感覚も含めて、とてもaodagさんらしいトークだったなあという印象でした。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=apischemathesis&gt;
&lt;h3&gt;APIのテストデータを自動生成できるSchemathesisの紹介&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;14:20 - 14:45&lt;/li&gt;
&lt;li&gt;&lt;p&gt;筒井 隆次 (@ryu22e)&lt;/li&gt;
&lt;li&gt;&lt;p&gt;APIのテストデータを自動生成できるSchemathesisの紹介&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-4"&gt;https://tokai.pycon.jp/2025/#session-talk-4&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://introduction-to-schemathesis.ryu22e.dev/"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;@ryu22e さんのトークは、Schemathesisを使ったAPIテストの自動化でした。&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; はOpenAPIドキュメントを使ってWebAPIエンドポイントをProperty-Based Testingで検証するテスティングツールです（詳しくはryu22eさんの資料 or &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/Schemathesis"&gt;https://scrapbox.io/shimizukawa/Schemathesis&lt;/a&gt; を参照）。&lt;/p&gt;
&lt;figure class=align-default id=id32&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk4.jpg"&gt;&lt;img alt="../../../../_images/talk4.jpg" src="https://www.freia.jp/taka/_images/talk4.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@ryu22e さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;&lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; が実装漏れのエッジケースを何度も見つけてくる状況に、「API実装を直したけど、まだコケる.. こんなデータでAPIエッジケースを見つけて来て正直ムカつきます」というぶっちゃけ感想から始まり、 &lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; がどうエッジケースを見つけてくるかを紹介してくれました。&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; は大量のテストケースを作りますが、キャッシュとテスト順序変更によって、次のテストでエラーになりそうなケースを優先的にテストして失敗時のエラーを早く出してくれるそうです。GitHub Actionsでこの動作を活かしたい場合は、 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;.hypothesis&lt;/span&gt;&lt;/code&gt; ディレクトリをキャッシュしておくと良いとのこと。&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; があれば「人間がテストを書かなくて良いのでは？」と考えるかもしれないが「そんなことはなかった」という結論でした。 &lt;a class="reference external" href="https://pypi.org/project/schemathesis/"&gt;Schemathesis&lt;/a&gt; のテストはどんなテストが行われるのか分からないしコントロールできず、テストコードから仕様を読み取れなくなるという課題があるそうです。使いどころは「エッジケースを見つける」「仕様と実装の乖離を見つける」というところ、ということでした。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id12&gt;
&lt;h3&gt;稼働中のバッチアプリケーションを依存性逆転の法則でモダナイズ&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;14:55 - 15:20&lt;/li&gt;
&lt;li&gt;&lt;p&gt;fujidomoe&lt;/li&gt;
&lt;li&gt;&lt;p&gt;稼働中のバッチアプリケーションを依存性逆転の法則でモダナイズ - 型安全と堅牢なテストによるリプレイス戦略&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-5"&gt;https://tokai.pycon.jp/2025/#session-talk-5&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;資料（見当たらず）&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;fujidomoeさんのトークは、エンジニアでない方が書いたPythonコードをモダナイズした事例でした。&lt;/p&gt;
&lt;figure class=align-default id=id33&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk5.jpg"&gt;&lt;img alt="../../../../_images/talk5.jpg" src="https://www.freia.jp/taka/_images/talk5.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;fujidomoe さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;ビジネスの根幹ではあるけど本番で動かすには安全ではないコードで、テストコードなし、試行錯誤の結果そのまま、Jupyter Notebookから始まったコードがほとんどそのまま本番バッチで動いている、という状態だったそうです。この状況を「dfが登場したら研究職と思え」と表現したのは、めっちゃ分かる。&lt;/p&gt;
&lt;p&gt;アンチパターンとして挙げられていたのは、大きく2つ。ひとつは &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;**kwargs&lt;/span&gt;&lt;/code&gt; で引数を処理していて、どこから何が渡ってくるのか見通しが悪くなっていること。もうひとつは、グローバル関数がたくさん増えてしまって、依存関係が分かりづらくなっていることでした。&lt;/p&gt;
&lt;p&gt;対策として、Pydanticの導入による型安全とパラメータの明示化、リポジトリパターンとDIP（依存性逆転の原則）の導入で、 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;collection.abc&lt;/span&gt;&lt;/code&gt; を使ってメソッドの実装を強制し、インフラレイヤーがインターフェースだけを把握すればよい設計にしたとのこと。&lt;/p&gt;
&lt;p&gt;対策としては、まず &lt;a class="reference external" href="https://pypi.org/project/pydantic/"&gt;Pydantic&lt;/a&gt; の導入によって、型安全とパラメータの明示を行ったこと。 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;dataclass&lt;/span&gt;&lt;/code&gt; では型チェックが行われないのに対して、&lt;a class="reference external" href="https://pypi.org/project/pydantic/"&gt;Pydantic&lt;/a&gt; を使うことで入力値のバリデーションをしっかり掛けられるようにしていました。次にリポジトリパターンとDIP（依存性逆転の原則）を導入し、 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;collections.abc&lt;/span&gt;&lt;/code&gt; を使ってメソッドの実装を強制することで、インフラレイヤー側は実装詳細ではなくインターフェースだけを把握すればよい構造にしていったとのこと。（私の活動領域ではこれはやり過ぎな気がするけど、Python標準で必要最小限の制約を加えているやりかたは良さそう）。&lt;/p&gt;
&lt;p&gt;また、環境構築手順をREADMEからMakefileへ移行し、&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;make&lt;/span&gt; &lt;span class=pre&gt;docker/setup&lt;/span&gt;&lt;/code&gt; で完結、&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;make&lt;/span&gt; &lt;span class=pre&gt;docker/test&lt;/span&gt;&lt;/code&gt; でテストも実行できるようにしたそうです。質疑応答で「READMEが秘伝のたれになると言うけどMakefileも秘伝のたれになるのでは」という@aodagさんの質問に対して、「READMEは文章なので劣化に気付きづらいが、Makefileは壊れるとすぐ分かるのでまだマシ」という回答でした。&lt;/p&gt;
&lt;p&gt;質疑応答では他に、Q「レイヤー構造化したことで逆に認知負荷が高まることはなかったか？」A「それ以前がノールールだったので、特に混乱はなかったです」。Q「レイヤー構造にみんながちゃんと沿ってくれるのか、どう強制するのか」A「もらうときは構造に沿ってなくても良いけど、そのまま本番に持っていくことは防いでいる。エンジニアが水際で防いでいます」というチームへの導入と運用の参考になりそうな話もありました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=fastapi-x&gt;
&lt;h3&gt;型でつなぐFastAPI x フロントエンド活用術&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;15:35 - 16:00&lt;/li&gt;
&lt;li&gt;&lt;p&gt;三浦 耕生（@k_miura_io）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;型でつなぐFastAPI × フロントエンド活用術&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-6"&gt;https://tokai.pycon.jp/2025/#session-talk-6&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.docswell.com/s/k_miura_io/Z8W39Y-2025-11-08-160729"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Miuraさんのトークは、FastAPIとフロントエンドの連携でした。名古屋のPython勉強会 &lt;a class="reference external" href="https://shachi-py.connpass.com"&gt;鯱.py&lt;/a&gt; の運営もされている方です。&lt;/p&gt;
&lt;figure class=align-default id=id34&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk6.jpg"&gt;&lt;img alt="../../../../_images/talk6.jpg" src="https://www.freia.jp/taka/_images/talk6.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@k_miura_io さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;FastAPIの特徴として、軽量、高速、柔軟なファイル構成、型ヒントによる堅牢なAPI設計、OpenAPIドキュメント自動生成を挙げていました。私はあまりOpenAPIネイティブなフレームワークを使えていないので、良いなあ使いたいなあと思いながら聞いてました。&lt;/p&gt;
&lt;p&gt;紹介してくれた &lt;a class="reference external" href="https://heyapi.dev/"&gt;Hey API&lt;/a&gt; は、OpenAPIドキュメントからTypeScript対応のAPIクライアントを生成してくれるツールで、FastAPIの公式で紹介されているそうです。&lt;/p&gt;
&lt;p&gt;&lt;a class="reference external" href="https://redocly.github.io/redoc/"&gt;redoc&lt;/a&gt; というツールも紹介されていて、Swagger-UIよりもドキュメントっぽい出力ができるとのこと。たしかにSwagger-UIはツールっぽい感じです。聞きながら、 &lt;a class="reference external" href="https://redocly.github.io/redoc/"&gt;redoc&lt;/a&gt; は &lt;a class="reference external" href="https://connpass.com/about/api/"&gt;connpassのAPI(v2)リファレンス&lt;/a&gt; にも採用されていることを思い出しました。&lt;/p&gt;
&lt;p&gt;質疑応答では、「Hey API知らなかったので勉強になりました。genというファイルは何者？(@terapyon)」A「genファイルはHey APIのアウトプットで、それを参照してクライアントを生成します」Q「Q. 本番で使っても大丈夫なもの？」A「大丈夫です」というやりとりがありました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id14&gt;
&lt;h3&gt;Pythonで構築する人口移動ナレッジグラフ&lt;/h3&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;16:05 - 16:30&lt;/li&gt;
&lt;li&gt;&lt;p&gt;丹野良介（@negi111111）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Pythonで構築する人口移動ナレッジグラフ: GraphRagを用いた意味的地域検索への応用&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://tokai.pycon.jp/2025/#session-talk-7"&gt;https://tokai.pycon.jp/2025/#session-talk-7&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://speakerdeck.com/negi111111/pythondegou-zhu-suruquan-guo-shi-ting-cun-naretuzigurahu-graphragwoyong-itayi-wei-de-di-yu-jian-suo-henoying-yong"&gt;資料&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;丹野さんのトークは、GraphRagを用いた意味的地域検索への応用でした。&lt;/p&gt;
&lt;figure class=align-default id=id35&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk7.jpg"&gt;&lt;img alt="../../../../_images/talk7.jpg" src="https://www.freia.jp/taka/_images/talk7.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@negi111111 さん（人口移動ナレッジグラフは時間の都合で間に合わず、タイトル変更とのこと）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;題材として使われていたのは SSDSE（Standardized Statistical Data Set for Education）という教育用標準データセットで、欠損値がなくデータ量も多く、解説PDFまで付いているという至れり尽くせりなデータセットとのこと。 &lt;a class="reference external" href="https://www.nstac.go.jp/use/literacy/ssdse/"&gt;SSDSE（教育用標準データセット） | 独立行政法人　統計センター&lt;/a&gt; で配布されています。公的機関がこういうちゃんとしたオープンデータを提供してくれてるんですね。&lt;/p&gt;
&lt;p&gt;データ分析そのものは、昔ながらの「Pandasでゴリゴリ書く」スタイルからだいぶ変わってきていて、Vive Coding に任せて使われるものになったとのこと。データ把握をしようと思ったら Google Spreadsheet 一択で、Gemini が内蔵されているので自然言語で質問しながら探索している、というのはかなり2025年っぽいワークフローだと感じました。&lt;/p&gt;
&lt;p&gt;テーブルデータから知識グラフ構造への変換ではNetworkXで扱えるグラフ構造に変換していきますが、ここもVive Codingに手伝ってもらって一発で作ってもらったそうです。スライドでは「知識グラフとは？」という図から始まり、RAGとは何か、そこからさらにGraphRAGとは何か、という流れで説明されていました（知識グラフって具体的に何？というのは私は掴みきれず）。&lt;/p&gt;
&lt;figure class=align-default id=id36&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/talk7-graph.jpg"&gt;&lt;img alt="../../../../_images/talk7-graph.jpg" src="https://www.freia.jp/taka/_images/talk7-graph.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;知識グラフとは&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;GraphRAG用のデータに変換したあとは、人口移動のデータを使って地域間の関係性をグラフとして表現し、意味的な地域検索に応用していく、というのがこのトークの肝です。ただし、知識グラフを動かすには、そこそこお金がかかるので注意、という現実的な話もありました。&lt;/p&gt;
&lt;p&gt;質疑応答では、「GraphRAGデータベースというのはMicrosoftのもの？」という質問に対して、「RAGをGraph構造に拡張したのはMicrosoftだけれど、GraphRAG自体はデータベースというより、ファイル群を作ってそれをクエリできるようにしているようなもの」という説明がありました（私はよく分からず.. Vector Database に入れている訳ではない…？）。また、「市と市のつながりは作った？」という質問には、「名古屋から三重に移動したデータがあるのでそれを使ったが、今回はデータの関係のみ（重みなし）で扱っている」という回答でした。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=id16&gt;
&lt;h2&gt;休憩&lt;/h2&gt;
&lt;p&gt;会場のテラスに出たところ。&lt;/p&gt;
&lt;figure class=align-default id=id37&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/building.jpg"&gt;&lt;img alt="../../../../_images/building.jpg" src="https://www.freia.jp/taka/_images/building.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;会場のテラス、去年作りかけだったビルが完成している！！&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;...と思ったら、まだ完成ではないらしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=lt&gt;
&lt;h2&gt;LT&lt;/h2&gt;
&lt;p&gt;当日募集のLTもあり、盛り上がりました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;16:50 - 17:10&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Lightning Talks&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;@attakei さん&lt;/p&gt;
&lt;figure class=align-default id=id38&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lt1.jpg"&gt;&lt;img alt="../../../../_images/lt1.jpg" src="https://www.freia.jp/taka/_images/lt1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@attakei さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;「oEmbedPyを使って、ドキュメントに◯◯◯を埋め込もう」&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://oembed.com/"&gt;oembed&lt;/a&gt; は民主的なフォーマットでメジャーどころは対応しているらしい&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://pypi.org/project/oEmbedPy/"&gt;oEmbedPy&lt;/a&gt; を使えばSphinxドキュメントに簡単にoembedフォーマットの◯◯を埋め込める&lt;/li&gt;
&lt;li&gt;&lt;p&gt;埋め込みたくて探したけどPyPIにあった他のPythonクライアントはどれもメンテされてなかったので自分で作った&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;みその （miso taku）さん&lt;/p&gt;
&lt;figure class=align-default id=id39&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lt2.jpg"&gt;&lt;img alt="../../../../_images/lt2.jpg" src="https://www.freia.jp/taka/_images/lt2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;みその （miso taku）さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;巡回セールスマン問題を数理最適化で解いてハシゴ酒の最短ルートを見つける（MIP, Google Maps API）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;巡回セールスマン問題とは、組み合わせが膨大で簡単には解けない問題&lt;/li&gt;
&lt;li&gt;&lt;p&gt;数理最適化を解く &lt;a class="reference external" href="https://pypi.org/project/mip/"&gt;MIP&lt;/a&gt; を使って最短距離でハシゴ酒するアプリをStreamlitで作成した&lt;/li&gt;
&lt;li&gt;&lt;p&gt;行ってきた -&amp;gt; 3軒でおなかいっぱい（会場笑&lt;/li&gt;
&lt;li&gt;&lt;p&gt;まとめ: ハシゴ酒に巡回セールスマン問題は必要ない&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;@takanory さん&lt;/p&gt;
&lt;figure class=align-default id=id40&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/lt3.jpg"&gt;&lt;img alt="../../../../_images/lt3.jpg" src="https://www.freia.jp/taka/_images/lt3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;@takanory さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;🐱絵文字をドキュメントにいれよう&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スライド: &lt;a class="reference external" href="https://slides.takanory.net/slides/20251108tokai/#/"&gt;https://slides.takanory.net/slides/20251108tokai/#/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id17&gt;
&lt;h2&gt;クロージング&lt;/h2&gt;
&lt;p&gt;昨年同様、運営の皆さんの温かい雰囲気で締めくくられました。&lt;/p&gt;
&lt;figure class=align-default id=id41&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/closing2.jpg"&gt;&lt;img alt="../../../../_images/closing2.jpg" src="https://www.freia.jp/taka/_images/closing2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;司会進行で「座長からのあいさつ」を全部しゃべっちゃったｗ（右端に見切れてる座長）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;プレゼント企画&lt;/p&gt;
&lt;figure class=align-default id=id42&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/prize1.jpg"&gt;&lt;img alt="../../../../_images/prize1.jpg" src="https://www.freia.jp/taka/_images/prize1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;おめでとうございます～&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id43&gt;
&lt;video controls src="../../../../_images/prize-dora.mp4" title="../../../../_images/prize-dora.mp4"&gt;
&lt;a href="https://www.freia.jp/taka/_images/prize-dora.mp4"&gt;../../../../_images/prize-dora.mp4&lt;/a&gt;
&lt;/video&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;盛り上げ役のドラがだんだん上手になっていく&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id18&gt;
&lt;h2&gt;感想&lt;/h2&gt;
&lt;p&gt;2回目の開催ということで、昨年よりも少しパワーアップした内容で、とても楽しいイベントでした。
イベント運営されたみなさん、スピーカーの皆さん、ありがとうございました！&lt;/p&gt;
&lt;p&gt;前回同様の1トラック構成は、聞く話を選べない代わりにどれを聞こうか迷うこともなく、そのおかげで普段聞かない分野のとても面白い話に出会えて良かったです。&lt;/p&gt;
&lt;figure class=align-default id=id44&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party3.jpg"&gt;&lt;img alt="../../../../_images/party3.jpg" src="https://www.freia.jp/taka/_images/party3.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;懇親会は、昨年と同じ &lt;a class="reference external" href="https://ymarket-nagoroba.com/"&gt;ワイマーケットのクラフト食堂 ナゴロバ&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id45&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party21.jpg"&gt;&lt;img alt="../../../../_images/party21.jpg" src="https://www.freia.jp/taka/_images/party21.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;二次会も、昨年と同じHUB&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id20&gt;
&lt;h2&gt;おまけ&lt;/h2&gt;
&lt;p&gt;東京から名古屋に行く新幹線は本数がかなり多いので、自由席でもホームで少し待てば好きな席が選べます。……というのを何も考えずに出発直前のに飛び乗ったので窓側の電源が確保出来ず。&lt;/p&gt;
&lt;p&gt;名古屋に着いてから、駅構内の"住よし"できしめんを頂きました。
去年はきつね。今年は山菜。次回はかき揚げにしよう。&lt;/p&gt;
&lt;figure class=align-default id=id46&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/kishimen1.jpg"&gt;&lt;img alt="../../../../_images/kishimen1.jpg" src="https://www.freia.jp/taka/_images/kishimen1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;住よし の きしめん（山菜）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;7:39 東海道新幹線 東京駅発&lt;/li&gt;
&lt;li&gt;&lt;p&gt;9:16 名古屋着&lt;/li&gt;
&lt;li&gt;&lt;p&gt;9:30 住よしできしめんを頂く&lt;/li&gt;
&lt;li&gt;&lt;p&gt;9:40 東山線 名古屋 発&lt;/li&gt;
&lt;li&gt;&lt;p&gt;9:50 東山線 栄 着&lt;/li&gt;
&lt;li&gt;&lt;p&gt;10:00 会場着（中日ホール）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;17:50 買い物（ベーカリーピカソ@三越）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;18:20 懇親会（ワイマーケットのクラフト食堂）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;21:38 地下鉄&lt;/li&gt;
&lt;li&gt;&lt;p&gt;21:43 名古屋駅着&lt;/li&gt;
&lt;li&gt;&lt;p&gt;21:50 東海道新幹線、名古屋発&lt;/li&gt;
&lt;li&gt;&lt;p&gt;23:39 東京駅着&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sun, 30 Nov 2025 22:00:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/11/pycontokai2025/index.html</guid></item><item><title>PyCon JP 2025 in 広島 に参加しました</title><link>https://www.freia.jp/taka/blog/2025/09/pyconjp2025/index.html</link><description>&lt;section id=pycon-jp-2025-in&gt;

&lt;p&gt;2025年9月26日から28日にかけて、PyCon JP 2025 に参加してきました。
広島初上陸です。&lt;/p&gt;
&lt;figure class=align-default id=id7&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jp2025-day1-opening.jpg"&gt;&lt;img alt="../../../../_images/jp2025-day1-opening.jpg" src="https://www.freia.jp/taka/_images/jp2025-day1-opening.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニング、座長のnishimotzさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;前回までは、2011年の PyCon JP 初開催からずっと東京で開催してきましたが、今回はじめて、東京以外での開催です。&lt;/p&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon JP 2025&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://2025.pycon.jp/"&gt;https://2025.pycon.jp/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;2025年9月26日(金) DAY1トーク、2日(土) DAY2トーク、3日(日) スプリント&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.pcf.city.hiroshima.jp/icch/"&gt;広島国際会議場&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;私は、前日夕方に名古屋に到着して、 DAY1、DAY2, スプリントの3日間参加して今帰りの新幹線です。
イベント参加者は無料で &lt;a class="reference external" href="https://hpmmuseum.jp/"&gt;広島平和記念資料館&lt;/a&gt; に入場できるので、スプリント中にちょっと行ってきました。&lt;/p&gt;
&lt;p&gt;参加時にトークのメモや質疑応答を書いたスクラップが以下にあります。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2025"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2025&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;ざっくり感想&lt;/h2&gt;
&lt;p&gt;私の今回のイベントでの役割は、トークプロポーザルが選考を通ったので発表者として、また一般社団法人PyCon JP Associationの会計理事として参加してきました。イベント直前はトーク準備（個人）、公開ミーティング準備（一社）、遠方支援作業（一社）にずっと追われていた感じですが、これもまた毎年秋の風物詩になってしまった感じがします。大変だけど楽しい。&lt;/p&gt;
&lt;figure class=align-default id=id8&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jp2025-my-talk.jpg"&gt;&lt;img alt="../../../../_images/jp2025-my-talk.jpg" src="https://www.freia.jp/taka/_images/jp2025-my-talk.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;私のトークに参加された皆さんと&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;初めての東京以外での開催でしたが、広島への新幹線移動4時間で肩が凝ったくらいで、特に困ったことはなくイベントも十分楽しめました。
イベント開催はちょっと聞いたところでは、初めての土地での開催はやっぱり大変だったそうです。イベント開催してくれた主催メンバーのみなさんありがとうございます。&lt;/p&gt;
&lt;p&gt;また、今回国内のイベントに3泊4日で参加してみて、こういった移動を毎年東京以外の人たちはやっていたのだなあと改めて思いました。そう思うと、東京以外での開催を場所を移しながら続けることは、遠方から参加しつづける大変さをみんなで分担するという意味でも良いことなんじゃないかと思いました。今回の1日目のキーノートのSebastiánの話にあった、OSSの保守をし続ける人に苦労を押しつけて楽に使っている状況（Bus Factor と Bus ticket factor）に似た構造なのかも、と重いました。&lt;/p&gt;
&lt;figure class=align-default id=id9&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jp2025-keynote1.jpg"&gt;&lt;img alt="../../../../_images/jp2025-keynote1.jpg" src="https://www.freia.jp/taka/_images/jp2025-keynote1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;1日目のキーノートのSebastián氏&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;2日目のキーノートでは、 &lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html"&gt;&lt;span class=doc&gt;書籍紹介: 『＃100日チャレンジ』プログラミング x ChatGPTで"自分だけのHACK"を見つけた挑戦譚&lt;/span&gt;&lt;/a&gt; で紹介した大塚さんがキーノートに登場しました。一番気になったのは "プログラミングが、「書くこと」から「問いを立てること」へ" という部分です。「問い」は私がこの1年ほど前から意識して気にしている事です。発表でもうちょっと「問うこと」についての洞察や、学会に参加したときの内容の抜粋などを聞きたかったなと思いました。&lt;/p&gt;
&lt;figure class=align-default id=id10&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jp2025-keynote2.jpg"&gt;&lt;img alt="../../../../_images/jp2025-keynote2.jpg" src="https://www.freia.jp/taka/_images/jp2025-keynote2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;2日目のキーノートの大塚氏&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;ところで、帰りにはお土産を買う訳ですが、イベント中に提供されたオヤツが広島土産の試食会だったんじゃないかと思うくらいたくさんの種類が提供されていて、帰りのお土産探しはかなり捗りました。あれはよかった。私は檸檬ドーナツ棒がお気に入りです。&lt;/p&gt;
&lt;figure class=align-default id=id11&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/jp2025-snacks.jpg"&gt;&lt;img alt="../../../../_images/jp2025-snacks.jpg" src="https://www.freia.jp/taka/_images/jp2025-snacks.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベント中のおやつ。瀬戸内レモンイカ天美味しかった&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;また来年も広島開催ということで、今回行けなかった宮島には次回行きたいです。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=pytest10&gt;
&lt;h2&gt;pytestを爆速にする10の方法&lt;/h2&gt;
&lt;p&gt;自分のトークセッションです。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;"pytestを爆速にする10の方法"&lt;/li&gt;
&lt;li&gt;&lt;p&gt;トーク概要 &lt;a class="reference external" href="https://2025.pycon.jp/ja/timetable/talk/ZFYREY"&gt;https://2025.pycon.jp/ja/timetable/talk/ZFYREY&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;9月27日（土） 14:05 - 14:35&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Video: 準備中&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Slide: &lt;a class="reference external" href="https://docs.google.com/presentation/d/e/2PACX-1vQa-xILa3uDHCdQH1li9_p7g48gYsUb8DfBRy-VetNAQtY-rGfMFsx9AVMPctpLIbGw9o09C0sv-SGA/pub"&gt;pytestを爆速にする10の方法&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;テストが爆速になると、色々なメリットがあります。
このトークでは、現実のWebサービス開発のコードを対象に、UnitTest実行時間を削減した10の方法を紹介しました。&lt;/p&gt;
&lt;p&gt;30分で50スライド。だいぶ早口だったと思います。
参加されたみなさん、お疲れ様でした &amp;amp; ありがとうございました。&lt;/p&gt;
&lt;p&gt;最後、10倍速になったテストの動作比較デモをしましたが、10倍速、インパクトがあったようで、好評でよかった。&lt;/p&gt;
&lt;blockquote&gt;
&lt;div&gt;&lt;iframe allowfullscreen=true frameborder=0 height=299 mozallowfullscreen=true src="https://docs.google.com/presentation/d/e/2PACX-1vQa-xILa3uDHCdQH1li9_p7g48gYsUb8DfBRy-VetNAQtY-rGfMFsx9AVMPctpLIbGw9o09C0sv-SGA/pubembed?start=false&amp;amp;loop=false&amp;amp;delayms=3000" webkitallowfullscreen=true width=480&gt;&lt;/iframe&gt;&lt;/div&gt;&lt;/blockquote&gt;
&lt;/section&gt;
&lt;section id=id6&gt;
&lt;h2&gt;おまけ&lt;/h2&gt;
&lt;p&gt;参加時にトークのメモや質疑応答を書いたスクラップが以下にあります。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2025"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2025&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;過去のPyCon JP 参加はblogはほとんど書いて無くて、以下にメモがありました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2018"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2018&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2019"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2019&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2020"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2020&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2021"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2021&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2022"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2022&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_JP_2024"&gt;https://scrapbox.io/shimizukawa/PyCon_JP_2024&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2017/09/pyconjp2017-day1/index.html"&gt;&lt;span class=doc&gt;PyCon JP 2017 1日目 参加ログ #pyconjp&lt;/span&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;こうして振り返ってみると、毎年参加しているのにblog記事にしたのは数回だけだったみたいです。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sun, 28 Sep 2025 23:40:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/09/pyconjp2025/index.html</guid></item><item><title>PyCon US 2025 in Pittsburg に参加しました</title><link>https://www.freia.jp/taka/blog/2025/05/pyconus2025/index.html</link><description>&lt;section id=pycon-us-2025-in-pittsburg&gt;

&lt;p&gt;2025年5月14日から22日にかけて、PyCon US 2025 に参加してきました。
私にとって、これが初めてのPyCon US参加で、ついに来た！という感じで楽しんできました。&lt;/p&gt;
&lt;figure class=align-default id=id6&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/us2025-day1-opening.jpg"&gt;&lt;img alt="../../../../_images/us2025-day1-opening.jpg" src="https://www.freia.jp/taka/_images/us2025-day1-opening.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニング、座長さんと、イベント中ずっと提供されていた文字起こし&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;これまでアジア圏のPyCoyや、EuroPythonなどの海外PyConに参加してきましたが、本家のPyConは未体験でした。
参加には、時間もお金もかかるし、参加する理由がそれほど無かったというのが正直なところです。&lt;/p&gt;
&lt;p&gt;ですが、行って良かった！また行きたい。&lt;/p&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon US 2025&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://us.pycon.org/2025/"&gt;https://us.pycon.org/2025/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;2025年5月15日(木) ～ 2025年5月22日(木)&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;アメリカ, Pittsburg&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;参加時にトークのメモや質疑応答を書いたスクラップが以下にあります。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_US_2025"&gt;https://scrapbox.io/shimizukawa/PyCon_US_2025&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;このイベント参加時について &lt;a class="reference external" href="https://docs.google.com/presentation/d/e/2PACX-1vR1tSG3NwDy3-Tkmgu3zQo7N8aT6I4K8rZcqiSBKGboPUV1woTtkXaEKCjfuT8xDFNAXvYpHJUfxIwO/pub"&gt;はじめてのPyCon US&lt;/a&gt; というスライドにまとめて &lt;a class="reference external" href="https://pyconjp.connpass.com/event/357582/"&gt;PyCon US 2025 参加報告会&lt;/a&gt; で紹介してきました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;ざっくり感想&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;イベント面白かった！&lt;/li&gt;
&lt;li&gt;&lt;p&gt;トークも役割も持たずに参加したので、そこは残念。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;せめてライトニングトークを、と2回応募して2回落選しました。。。最初の募集をスルーしたのがよくなかった&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Sprintに1日参加して、t-stringsに少し貢献できたのが良かった&lt;/li&gt;
&lt;li&gt;&lt;p&gt;キーノートはプログラミング言語の話はあまりなく、先端を走るPyCon USらしいと思いつつ、難しくて、楽しいという感じではなかったな&lt;/li&gt;
&lt;li&gt;&lt;p&gt;アメリカ入国は最近のUS事情を事前に聞いてはビクビクしたけど特に何事もなく。&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h2&gt;おまけ&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;ピッツバーグからシカゴまで交代で運転したのも楽しかった&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.youtube.com/watch?v=rDjYzlPW7hM&amp;amp;t=1367s"&gt;PyCon US 2025帰りのドライブ中に振り返り - YouTube&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;帰りの飛行機内で誕生日を迎えました&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2025/05/birthday50/index.html"&gt;&lt;span class=doc&gt;50歳 - 日付変更線で誕生日&lt;/span&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Thu, 22 May 2025 23:59:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/05/pyconus2025/index.html</guid></item><item><title>50歳 - 日付変更線で誕生日</title><link>https://www.freia.jp/taka/blog/2025/05/birthday50/index.html</link><description>&lt;section id=id1&gt;

&lt;p&gt;50歳です。PyCon US 2025 からの帰りの飛行機で、日付変更線を越えて誕生日を迎えました。&lt;/p&gt;
&lt;figure class=align-default id=id2&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/dateline.jpg"&gt;&lt;img alt="../../../../_images/dateline.jpg" src="https://www.freia.jp/taka/_images/dateline.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;日付変更線を越えたあたり&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;日本時間の10時くらいに日付変更線を越えているので、誕生日が14時間しかない、ということになるのだろうか？
タイムゾーンを何度もまたいで移動したので、けっこうよく分からなくなっている...。&lt;/p&gt;
&lt;p&gt;夕食は誕生日プラン（賑やかなケーキが出てくる）で家族にお祝いしてもらって、食後のアンケートで「年齢」欄の「～49歳」を一回選んでから、「50歳～」を選び直した。&lt;/p&gt;
&lt;/section&gt;
</description><pubDate>Thu, 22 May 2025 22:40:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/05/birthday50/index.html</guid></item><item><title>Nuxt3 向け、スクロール位置復元モジュールの実装とnpmjs公開</title><link>https://www.freia.jp/taka/blog/2025/05/nuxt-scroll-restoration/index.html</link><description>&lt;section id=nuxt3-npmjs&gt;

&lt;p&gt;SPAアプリでF5リロードした時に、スクロール位置が復元されない問題を解決するためのNuxt3モジュール &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;nuxt-scroll-restoration&lt;/span&gt;&lt;/code&gt; を作成し、npmで公開しました。これが、私のnpmで初めてのリリースになりました。&lt;/p&gt;
&lt;figure class=align-default id=id9&gt;
&lt;img alt="../../../../_images/nuxt-scroll-restoration-on-npmjs.png" src="https://www.freia.jp/taka/_images/nuxt-scroll-restoration-on-npmjs.png"&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;npmjs での表示&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;section id=id1&gt;
&lt;h2&gt;モチベーション&lt;/h2&gt;
&lt;p&gt;Nuxtでアプリを作ると、リロード時にスクロール位置が復元されません。
ページ編集結果を確認するためにリロードしたら、スクロール位置が失われて先頭が表示されてしまうため、共同編集中などにとても不便です。&lt;/p&gt;
&lt;p&gt;従来のHTMLサイトではブラウザ標準のスクロール位置復元機能が働きますが、NuxtのようなSPAではそれが期待通りに動作しません。&lt;/p&gt;
&lt;p&gt;解決策を探しているうちに &lt;a class="reference external" href="https://github.com/janpaul123/delayed-scroll-restoration-polyfill"&gt;delayed-scroll-restoration-polyfill&lt;/a&gt; を見つけましたが、これはJS一般用の実装だったため、Nuxt向けにそのままでは使えませんでした。そこで、Nuxt3用に調整したパッケージを作りました。&lt;/p&gt;
&lt;p&gt;最近は AI Agent でコーディングしていることもあり、それほど時間をかけずにパッケージ公開まで出来るんじゃないだろうか？と思えたことも、動機の１つです。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id2&gt;
&lt;h2&gt;前提&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;Node 18+&lt;/li&gt;
&lt;li&gt;&lt;p&gt;TypeScript&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Nuxt 3.9+&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://github.com/janpaul123/delayed-scroll-restoration-polyfill"&gt;delayed-scroll-restoration-polyfill&lt;/a&gt; (参考実装)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;コードはGitHubで公開しています：&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://github.com/shimizukawa/nuxt-scroll-restoration"&gt;https://github.com/shimizukawa/nuxt-scroll-restoration&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;npmパッケージ：&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://www.npmjs.com/package/nuxt-scroll-restoration"&gt;https://www.npmjs.com/package/nuxt-scroll-restoration&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id3&gt;
&lt;h2&gt;実装アプローチ&lt;/h2&gt;
&lt;p&gt;実装にあたって、 &lt;a class="reference external" href="https://github.com/janpaul123/delayed-scroll-restoration-polyfill"&gt;delayed-scroll-restoration-polyfill&lt;/a&gt; というパッケージを参考にしました。このコードをAI Agent（GitHub Copilot Agent + Sonnet 3.7）に参照させました。&lt;/p&gt;
&lt;p&gt;まずは手元のNuxt3アプリ向けプラグインとして動作するようにコードを調整させました。数回の会話でそれなりに動作する状態になりましたが、Nuxt3は開発モードが重いので、「リロード後にスクロール位置が復元される」のを確認する人間側の作業にけっこう時間がかかりました。&lt;/p&gt;
&lt;p&gt;次にnpmjsでパッケージ公開できるようにパッケージ化してもらいました。
自分自身はJSのパッケージを作ったことがありませんが、まあまあ良さそうな &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;package.json&lt;/span&gt;&lt;/code&gt; が作れたと思います。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=archietecture&gt;
&lt;h2&gt;動作の仕組み / Archietecture&lt;/h2&gt;
&lt;p&gt;このモジュールは以下のアーキテクチャでスクロール位置を復元します。&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;ブラウザの標準スクロール復元機能（ &lt;a class="reference external" href="https://developer.mozilla.org/ja/docs/Web/API/History/scrollRestoration"&gt;history.scrollRestoration&lt;/a&gt; ）を無効化&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Historyのstate操作をフックして、現在のスクロール位置を記録&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ページ遷移後、保存したスクロール位置に復元を試みる&lt;/li&gt;
&lt;li&gt;&lt;p&gt;動的コンテンツの読み込みを考慮して、一定時間スクロール復元を繰り返し試行&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="highlight-typescript notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=c1&gt;// history APIの操作をオーバーライド&lt;/span&gt;
&lt;span class=kd&gt;const&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;originalPushState&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nb&gt;window&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;history&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;pushState&lt;/span&gt;&lt;span class=p&gt;;&lt;/span&gt;
&lt;span class=nb&gt;window&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;history&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;pushState&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kd&gt;function&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;(...&lt;/span&gt;&lt;span class=nx&gt;args&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=c1&gt;// 現在のスクロール位置を保存&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=nx&gt;state&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=o&gt;=&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;...&lt;/span&gt;&lt;span class=nx&gt;state&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=nx&gt;__scrollX&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;window.scrollX&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=nx&gt;__scrollY&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;window.scrollY&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=k&gt;return&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;originalPushState&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;apply&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nb&gt;window&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;history&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;args&lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;
&lt;span class=p&gt;};&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;この実装では、History APIを上書きしてスクロール位置を記録し、popstate時やページロード後にその位置に復元します。また、コンテンツが非同期に読み込まれる場合に備えて、一定時間をかけてスクロール位置の復元を試みます。&lt;/p&gt;
&lt;section id=id4&gt;
&lt;h3&gt;シーケンス図&lt;/h3&gt;
&lt;p&gt;動作の流れを以下のシーケンス図で表現します。&lt;/p&gt;
&lt;pre class=mermaid&gt;        sequenceDiagram
    participant Browser as ブラウザ
    participant NuxtApp as Nuxtアプリ
    participant HistoryAPI as window.history
    participant DOM as DOM

    Browser-&amp;gt;&amp;gt;NuxtApp: Nuxtアプリケーションの読み込み
    NuxtApp-&amp;gt;&amp;gt;HistoryAPI: scrollRestorationを"manual"に設定
    Note over HistoryAPI: ブラウザの標準スクロール復元を無効化

    NuxtApp-&amp;gt;&amp;gt;HistoryAPI: pushStateとreplaceStateをオーバーライド
    Note over HistoryAPI: スクロール位置をstateに保存するフック

    NuxtApp-&amp;gt;&amp;gt;NuxtApp: app:mountedフック
    Note over NuxtApp: アプリが完全にマウントされたことを確認

    Browser-&amp;gt;&amp;gt;NuxtApp: ナビゲーション実行（リンククリックなど）
    NuxtApp-&amp;gt;&amp;gt;HistoryAPI: 現在のスクロール位置を保存するreplaceState呼び出し
    HistoryAPI-&amp;gt;&amp;gt;HistoryAPI: state内に__scrollXと__scrollYを保存

    Browser-&amp;gt;&amp;gt;NuxtApp: ページリロードまたはナビゲーション実行
    NuxtApp-&amp;gt;&amp;gt;NuxtApp: page:finishフック
    Note over NuxtApp: ナビゲーション後にスクロール位置を復元

    NuxtApp-&amp;gt;&amp;gt;HistoryAPI: 保存されたスクロール位置をstateから確認
    alt stateに有効なスクロール位置がある場合
        NuxtApp-&amp;gt;&amp;gt;DOM: 保存された位置へのスクロール試行
        loop タイムアウトまたはスクロール成功まで
            DOM-&amp;gt;&amp;gt;DOM: スクロールが可能か確認
        end
    else 有効なスクロール位置がない場合
        NuxtApp-&amp;gt;&amp;gt;DOM: トップ(0, 0)へスクロール
    end

    Browser-&amp;gt;&amp;gt;NuxtApp: popstateイベント発生
    NuxtApp-&amp;gt;&amp;gt;HistoryAPI: イベントからstateを取得
    HistoryAPI-&amp;gt;&amp;gt;NuxtApp: 保存されたスクロール位置を提供
    NuxtApp-&amp;gt;&amp;gt;DOM: スクロール位置を復元
    &lt;/pre&gt;&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h3&gt;適切なフックポイントの調査&lt;/h3&gt;
&lt;p&gt;シーケンス図で、 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;page:finish&lt;/span&gt;&lt;/code&gt; と書きましたが、これが良いフックポイントなのかはよく分かっていません。
手元のNuxt3アプリではうまくいくようですが、Nuxt3プレイグランドではうまくいきませんでした。&lt;/p&gt;
&lt;p&gt;そこで、次のようなテストプラグインを実装して、フックポイントを調査しました。&lt;/p&gt;
&lt;div class="highlight-typescript notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=k&gt;import&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kr&gt;type&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;Router&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kr&gt;from&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=s2&gt;"vue-router"&lt;/span&gt;&lt;span class=p&gt;;&lt;/span&gt;

&lt;span class=k&gt;export&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=k&gt;default&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;defineNuxtPlugin&lt;/span&gt;&lt;span class=p&gt;((&lt;/span&gt;&lt;span class=nx&gt;nuxtApp&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;=&amp;gt;&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=nx&gt;console&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;log&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"plugin"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=s2&gt;"test.ts"&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=k&gt;for&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=kd&gt;const&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;key&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=k&gt;of&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;[&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:created"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:error"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:error:cleared"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:data:refresh"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"vue:setup"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"vue:error"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:rendered"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:redirected"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:beforeMount"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:mounted"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"app:suspense:resolve"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"link:prefetch"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"page:start"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"page:finish"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s2&gt;"page:transition:finish"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;])&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=c1&gt;// console.log("# register nuxtApp.hook", key);&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=nx&gt;nuxtApp&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;hook&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;key&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;()&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;=&amp;gt;&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;      &lt;/span&gt;&lt;span class=nx&gt;console&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;log&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"nuxt"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;key&lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;});&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;

&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;nuxtApp&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;$router&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kr&gt;as&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;Router&lt;/span&gt;&lt;span class=p&gt;).&lt;/span&gt;&lt;span class=nx&gt;beforeResolve&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;to&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;from&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;=&amp;gt;&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;      &lt;/span&gt;&lt;span class=nx&gt;console&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;log&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"router"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=s2&gt;"beforeResolve"&lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;

&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;nuxtApp&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;$router&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kr&gt;as&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;Router&lt;/span&gt;&lt;span class=p&gt;).&lt;/span&gt;&lt;span class=nx&gt;beforeEach&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;to&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;from&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;=&amp;gt;&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;      &lt;/span&gt;&lt;span class=nx&gt;console&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;log&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"router"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=s2&gt;"beforeEach"&lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;

&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;nuxtApp&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;$router&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kr&gt;as&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;Router&lt;/span&gt;&lt;span class=p&gt;).&lt;/span&gt;&lt;span class=nx&gt;afterEach&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=nx&gt;to&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;from&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;RouteLocationNormalized&lt;/span&gt;&lt;span class=p&gt;)&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;=&amp;gt;&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;      &lt;/span&gt;&lt;span class=nx&gt;console&lt;/span&gt;&lt;span class=p&gt;.&lt;/span&gt;&lt;span class=nx&gt;log&lt;/span&gt;&lt;span class=p&gt;(&lt;/span&gt;&lt;span class=s2&gt;"router"&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=s2&gt;"afterEach"&lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;);&lt;/span&gt;

&lt;span class=p&gt;});&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;この後、ブラウザの開発コンソールとにらめっこしながら、良さそうなフックポイントを決めました。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
&lt;section id=jsnpmjs&gt;
&lt;h2&gt;JSモジュール作成とnpmjs公開&lt;/h2&gt;
&lt;p&gt;npmjsでパッケージ公開できるようにパッケージ化する作業は、 AI Agent がやってくれました。やってくれたのですが、さすがに何も知らないままリリースするのはどうかと思い、 &lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;npm&lt;/span&gt; &lt;span class=pre&gt;run&lt;/span&gt; &lt;span class=pre&gt;dev&lt;/span&gt;&lt;/code&gt; で実行されるプレイグラウンド（デモ）の動作くらいは確認しようかと思いました。そこで、手元のNuxt3アプリでは動作しても、プレイグラウンドでは動作しないことに気付いてしまい、良い感じに動作するよう調整するのに数時間かかりました。&lt;/p&gt;
&lt;p&gt;また、READMEドキュメントは日英を用意しましたが、どちらも AI Agent が書いてくれたものを微調整した程度で採用しました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id6&gt;
&lt;h2&gt;使い方&lt;/h2&gt;
&lt;p&gt;Nuxtプロジェクトに以下のようにインストールし、pluginとして設定します。&lt;/p&gt;
&lt;div class="highlight-bash notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;npm&lt;span class=w&gt; &lt;/span&gt;install&lt;span class=w&gt; &lt;/span&gt;nuxt-scroll-restoration
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;code class="docutils literal notranslate"&gt;&lt;span class=pre&gt;nuxt.config.ts&lt;/span&gt;&lt;/code&gt; に追加：&lt;/p&gt;
&lt;div class="highlight-typescript notranslate"&gt;&lt;div class=highlight&gt;&lt;pre&gt;&lt;span&gt;&lt;/span&gt;&lt;span class=k&gt;export&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=k&gt;default&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=nx&gt;defineNuxtConfig&lt;/span&gt;&lt;span class=p&gt;({&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=kr&gt;module&lt;/span&gt;&lt;span class=nx&gt;s&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;[&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=s1&gt;'nuxt-scroll-restoration'&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;],&lt;/span&gt;

&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=c1&gt;// オプション設定（任意）&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=nx&gt;scrollRestoration&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=p&gt;{&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=nx&gt;scrollRestorationTimeoutMs&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;3000&lt;/span&gt;&lt;span class=p&gt;,&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=c1&gt;// 最大試行時間（ミリ秒）&lt;/span&gt;
&lt;span class=w&gt;    &lt;/span&gt;&lt;span class=nx&gt;tryToScrollIntervalMs&lt;/span&gt;&lt;span class=o&gt;:&lt;/span&gt;&lt;span class=w&gt; &lt;/span&gt;&lt;span class=kt&gt;50&lt;/span&gt;&lt;span class=w&gt;        &lt;/span&gt;&lt;span class=c1&gt;// 試行間隔（ミリ秒）&lt;/span&gt;
&lt;span class=w&gt;  &lt;/span&gt;&lt;span class=p&gt;}&lt;/span&gt;
&lt;span class=p&gt;})&lt;/span&gt;
&lt;/pre&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;これで、ブラウザバックやリロード時にスクロール位置が復元されるようになります。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id7&gt;
&lt;h2&gt;制限事項&lt;/h2&gt;
&lt;p&gt;このモジュールにはいくつかの制限事項があります：&lt;/p&gt;
&lt;ol class="arabic simple"&gt;
&lt;li&gt;&lt;p&gt;ブラウザのHistory APIサポートが必要（ほとんどのモダンブラウザは対応済み）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;動的コンテンツの読み込みタイミングによっては正確な復元が難しい場合がある&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スクロール復元の最大試行時間は3秒（デフォルト）&lt;/li&gt;
&lt;/ol&gt;
&lt;/section&gt;
&lt;section id=id8&gt;
&lt;h2&gt;まとめ&lt;/h2&gt;
&lt;p&gt;Nuxtモジュールを作成して公開することで、他のNuxtユーザーにも便利な機能を提供できると思いますが、それよりも、仕事のコードから分離することで個人的に探究することができ、ついでにnpmjsでパッケージ公開するところまで出来ました。&lt;/p&gt;
&lt;p&gt;実装自体はそれほど複雑ではありませんが、Nuxtのローディング処理のどこに差し込むとよいかを測るのはけっこう大変でした。これをモジュール化することで再利用性が高まり、導入も簡単になります。また、個人開発のパッケージにすることで、仕事の都合で雑多な処理が入り込むこともなくなり独立性を確保出来ました。&lt;/p&gt;
&lt;p&gt;今のところ、シンプルな目的が達成できているのでこれ以上機能追加することはないような気がしていますが、今回対応していない機能もいくつかあります。例えば、textareaのスクロール位置の復元には対応していません。また、アプリによってはうまく適合しない可能性もあります。フィードバックをもらえたら修正、機能追加してみようと思います。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Sat, 10 May 2025 01:00:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/05/nuxt-scroll-restoration/index.html</guid></item><item><title>PyCon APAC 2025 in Philippines に参加しました</title><link>https://www.freia.jp/taka/blog/2025/03/pyconapac2025/index.html</link><description>&lt;section id=pycon-apac-2025-in-philippines&gt;

&lt;p&gt;3月頭にフィリピンで開催された、PyCon APAC 2025に参加しました。&lt;/p&gt;
&lt;figure class=align-default id=id7&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-opening.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-opening.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-opening.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニング、共同座長のサイラスさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;昨年2月に参加したPyCon Philippines 2024からちょうど1年です。
前回参加時よりも、イベント全体は少しだけ落ち着いた雰囲気に感じたのは会場が大学だったからかもしれません。
大学の広い敷地を活用して、屋外のポスター展示や、その近くのコーヒー／アイスクリーム配布などがあり、開放的な雰囲気がありました。&lt;/p&gt;
&lt;p&gt;また、今回はAPACの名前を冠したことで外国からの参加者が多かったと思います。また、日本からも10名以上が参加していました。
それもあって、現地コミュニティーの方と交流する時間よりも、日本からの参加者や、各国のAPACオーガナイザー関係者との交流が多くなりました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2024/02/pyconph2024/index.html"&gt;&lt;span class=doc&gt;PyCon PH 2024 に参加しました&lt;/span&gt;&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2024/10/pyconapac2024/index.html"&gt;&lt;span class=doc&gt;PyCon APAC 2024 in インドネシア に参加しました&lt;/span&gt;&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon APAC 2025&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://pycon-apac.python.ph/"&gt;https://pycon-apac.python.ph/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;2025年3月1日(土)DAY1トーク、2日(日)DAY2トーク、3日(月)DAY3スプリント&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;Ateneo de Manila University (Leong Hall)&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;私は、DAY1、DAY2に参加しました。
前日の金曜夜に現地到着して、月曜朝には帰るスケジュールにしたため、DAY3のスプリントと、さらに翌日に開催された観光ツアーには参加しませんでした。&lt;/p&gt;
&lt;p&gt;参加時にトークのメモや質疑応答を書いたスクラップが以下にあります。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_APAC_2025"&gt;https://scrapbox.io/shimizukawa/PyCon_APAC_2025&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;イベントレポートが公開されています（参加した池田さん執筆）。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://gihyo.jp/article/2025/03/pycon-apac-2025"&gt;PyCon APAC 2025参加レポート | gihyo.jp&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;来週、4月4日（金）に、参加報告会が実施されます。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;&lt;a class="reference external" href="https://pyconjp.connpass.com/event/349628/"&gt;PyCon APAC 2025 参加報告会 - connpass&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default id=id8&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-venue.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-venue.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-venue.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;会場はマニラ首都圏のクバオ。&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;Terminal3（空港）から、宿泊したRed Hotelまで、Grab（タクシー）で日中だと2時間。
右上の会場までさらに30分。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id9&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-reception.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-reception.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-reception.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;受付（中央）と、スポンサーブース（壁ぞい）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id2&gt;
&lt;h2&gt;総括&lt;/h2&gt;
&lt;p&gt;PyCon APAC 2025は、1年前のPyCon PH 2024に比べて落ち着いた感じ。日本のPyCon JPっぽさを感じました。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;質疑応答は日本よりも積極的な感じなのは変わらず。みなさんガンガン質問していました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;イベント運営も素晴らしかった。APACとして開催するのが決まったのが11月頃だったので、元々PyCon PHをこの時期に開催する予定だったとしても看板掛け替えはけっこう大変だったろうと思う&lt;/li&gt;
&lt;li&gt;&lt;p&gt;全体写真撮影をメインホールで行った後、屋外でも撮ったのは驚きました。この人数で移動するの！？&lt;/li&gt;
&lt;li&gt;&lt;p&gt;イベント中に使えるWiFiは無し。今回は27GBのSIMを（目論見を外した結果）用意していたので、困りませんでした。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;日本からは参加者&amp;amp;スピーカーとして13名参加しました。自分を含む9名がトークやパネルで登壇しました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スポンサーブースは8テーブルほどで、2日間ともに活気があり、参加者みんなブースをよく廻っていました。スタンプラリー集めに積極的だったのかも？今回は日本の企業スポンサーは無し。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;エスプレッソコーヒーが1日1杯無料で、2杯目からは有料でした。他に無料のアイスクリームとタホがありました。暑い屋外でトーク後に食べるアイスクリームはめちゃくちゃ美味しかった。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;ランチは2日ともフィリピン料理のお弁当でした。フィリピン料理は辛いものが少なく、炭水化物が多め。1日目はチキンとパスタとライス。2日目はフィッシュと炒め野菜とライス。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;全体の公式パーティーは無く、1日目にスピーカーと各国オーガナイザーの招待パーティーに参加しました。当然のようにお酒は無し（アジアのPyConではお酒が出る国の方が少ない）。パーティー後は日本からのメンバーでビールを求めて移動。&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id3&gt;
&lt;h2&gt;自分のトークセッション&lt;/h2&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;日時場所&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;3月1日（土） 13:15 - 13:45&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Video: 準備中&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Slide: &lt;a class="reference external" href="https://docs.google.com/presentation/d/1lBd0d2z6urUl0bqpGZmM1KJ1eEzaDVmrSJXMTy-ywuQ/edit"&gt;"Structlog in Practice"&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;"Structlog in Practice"&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;PyCon JP 2024 で話した「実践Structlog」を英語にしたもの（ &lt;a class="reference internal" href="https://www.freia.jp/taka/blog/2024/10/pyconapac2024/index.html"&gt;&lt;span class=doc&gt;PyCon APAC 2024&lt;/span&gt;&lt;/a&gt; と同じ）です。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;クラウド時代のオススメロギングライブラリとしてstructlogの入門と実践で利用している事例を紹介しました。&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;figure class=align-default id=id10&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-shimizukawa-talk.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-shimizukawa-talk.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-shimizukawa-talk.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;私のトーク、恒例の演台から写真&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;ul&gt;
&lt;li&gt;&lt;p&gt;質疑応答など&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;トーク後には質疑応答が2つありました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;質問内容は、ログの集約と構造化をベンダー非依存で行いたいというニーズから来るものでした。私のトーク内では「ベンダー非依存でやりたいよね」というメッセージは含めていませんでしたが、そういうニーズは確実に存在するんだと実感しました。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;トーク後に、「PyCon APAC 2024 のインドネシアでトーク聞きました」と声をかけてもらえました。びっくり。&lt;/li&gt;
&lt;li&gt;&lt;p&gt;翌日のランチで同じ席になった方から、昨日のトーク聞きました、LinkedInにポストした写真のここです、と声をかけてもらえました。&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;p&gt;トークフィードバック&lt;/p&gt;
&lt;p&gt;後日、運営チームからトークへのフィードバックを共有いただきました。良い感触だったようで良かった。&lt;/p&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;役に立つ話題でした。ありがとう! （Practically useful topic. Thank you!）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;LokiやElasticSeatchへのログ記録など、例があるといいです。発表ありがとう。（want to get examples like logging to loki and elasticseatch. thanks for your speech）&lt;/li&gt;
&lt;li&gt;&lt;p&gt;良い話でしたが、もっと例を共有する時間があればもっと良かったです。（insightful talk, but would be better if we have time to share additional examples）&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;こういうフィードバックをもらえるの、良いな～。&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;イベント感想&lt;/h2&gt;
&lt;p&gt;この1年ちょっとで、フィリピン、日本、インドネシア（APAC）、東海、静岡、フィリピン（APAC）、とPyConに参加してきました。どのイベントも構成は異なっていますが、今回のフィリピンはAPAC地域の顔見知りが多数参加していたこともあってか、昨年のフィリピンとは違うような、APACイベント感があったような気がしました。&lt;/p&gt;
&lt;p&gt;何にしても、イベントは楽しかった！なにより、トーク発表をしたことで色々な人に声をかけてもらえたのが嬉しかったです。&lt;/p&gt;
&lt;figure class=align-default id=id11&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-jpteam.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-jpteam.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-jpteam.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;日本チームの集合写真。みんな良い笑顔～&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;次は、5月15日（木）から、1度は行ってみたかった &lt;a class="reference external" href="https://us.pycon.org/2025/"&gt;PyCon US 2025&lt;/a&gt; に参加してきます。
トーク予定はありませんが、LTは応募したい。どうなるかなー。（英語特訓始めました）&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h2&gt;写真で紹介&lt;/h2&gt;
&lt;p&gt;イベント前日。日本から到着して野良前夜祭へ参加。&lt;/p&gt;
&lt;figure class=align-default id=id12&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-naia3-jeepney.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-naia3-jeepney.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-naia3-jeepney.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;空港にあるジプニー（伝統的な乗り合いバス）。乗る度胸はない&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;乗り方: 飛び乗る&lt;/li&gt;
&lt;li&gt;&lt;p&gt;降り方: 声かける&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id13&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-turon.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-turon.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-turon.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;TURON、25ペソ（約70円）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;サババナナとジャックフルーツの揚げ春巻き。
SM（デパート）の地下に大抵あるスーパーマーケットのフードコートで売ってます。
美味しいのでフィリピン行ったら是非。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id14&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-omiyage-colgate.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-omiyage-colgate.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-omiyage-colgate.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Colgate（歯磨き粉）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;SMスーパーマーケットでお土産購入。
Colgate Whiteはホワイトニング効果が高くて、フィリピンだと大分安く購入できる。
（帰りに空港で没収された…100ml制限…）&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id15&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-jpteam-chikin.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-jpteam-chikin.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-jpteam-chikin.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;チキンの丸焼き（多分アドボ）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;日本メンバーの野良前夜祭に合流して夕食&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id16&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-jpteam-ikaring.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-jpteam-ikaring.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-jpteam-ikaring.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;カラマリ（イカリングフライ）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id17&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-lawson-icecream.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-lawson-icecream.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-lawson-icecream.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;でっかいアイスクリーム、330ペソ（約900円）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;ホテル下のローソンにて。
フィリピンのアイスは大きい（このサイズでよく売ってる）。
住んでたときによく食べてたロッキーロード、懐かしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id18&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-lawson.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-lawson.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-lawson.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ローソンのレジ&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;日本と似たレイアウトだけど、揚げ物コーナーが大きい&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id19&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day0-redhotel.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day0-redhotel.jpg" src="https://www.freia.jp/taka/_images/ph2025-day0-redhotel.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;宿泊したRed Hotel Cubao の部屋。1泊約4000円&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;イベント1日目。&lt;/p&gt;
&lt;figure class=align-default id=id20&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-coffee.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-coffee.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-coffee.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;1日1杯無料のコーヒー&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;Americano = エスプレッソのお湯割り&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Longblack = お湯に注いだエスプレッソ&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id21&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-warroom.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-warroom.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-warroom.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;War Room（スタッフ兼スピーカー部屋）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;トークの準備をするスピーカーのみなさん。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id22&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-treat-bukopie.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-treat-bukopie.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-treat-bukopie.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Buko Pie （ココナッツパイ）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;めっちゃ美味しい。スピーカーにこういう差し入れをもらえるのも嬉しい。
フォークとかは無いので、みんなで手でちぎって食べてました。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id23&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-lunch-space.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-lunch-space.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-lunch-space.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ランチ会場&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;会場まで長い長い行列で、全然進まないので写真だけ撮った。
時間をずらして後で食べることにしました。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id24&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-lunch-chikin.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-lunch-chikin.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-lunch-chikin.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;1日目ランチ、チキン&amp;amp;パスタ弁当&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;フィリピン人はチキン、パスタ、ライスが大好き（というイメージ）
味付けは濃いめ。野菜が欲しくなるけど、野菜はなかなか見かけない。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id25&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-booth-apac.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-booth-apac.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-booth-apac.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;PyCon APAC ブースの寺田さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id26&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-snack-kakanin.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-snack-kakanin.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-snack-kakanin.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントおやつの「カカニン」&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;カカニンは、ココナッツミルクともち米で作るらしい。
フィリピン版おはぎ？ 色んな味があった。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id27&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-ginos-member1.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-ginos-member1.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-ginos-member1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;日本メンバーでカンパイ&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;1日目終了後、会場から徒歩10分ほどの GINO'S BRICK OVENPIZZA&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id28&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-ginos-member2.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-ginos-member2.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-ginos-member2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;日本メンバーでクラフトビール&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;MITCHELL'S BACKYARD BREWERY。
ピザ屋の奥に醸造エリアがあるらしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id29&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-ginos-salada.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-ginos-salada.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-ginos-salada.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Salada with Burrata&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;ピザ屋のサラダ、みんなで「生野菜久しぶりーーー！！」と食べた。
Burrataは水牛のフレッシュチーズ。モッツァレッラチーズの仲間らしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id30&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day1-inviting-dinner.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day1-inviting-dinner.jpg" src="https://www.freia.jp/taka/_images/ph2025-day1-inviting-dinner.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;招待ディナー、Philippines料理たくさん&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;10種類くらいあったけど写真撮り忘れました。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;イベント2日目。&lt;/p&gt;
&lt;figure class=align-default id=id31&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-transcript.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-transcript.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-transcript.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;&lt;a class="reference external" href="https://otter.ai/"&gt;Otter&lt;/a&gt; リアルタイム文字起こし&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;&lt;a class="reference external" href="https://gihyo.jp/article/2025/03/pycon-apac-2025"&gt;参加レポート記事&lt;/a&gt; を執筆した池田さんが &lt;a class="reference external" href="https://otter.ai/"&gt;Otter&lt;/a&gt; で英語リアルタイム文字起こししていたので、聞きながら目で追ってました。英語聞き取りが追いつかなかったので、ありがたい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id32&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-lunch-fish.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-lunch-fish.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-lunch-fish.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントランチ2: 魚の揚げ物、サヤインゲン炒め、米&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;味はやっぱり濃いめ。飯が進む。
フィリピン人は揚げ物も好き。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id33&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-lunch-people.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-lunch-people.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-lunch-people.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントランチ2: 目閉じ&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;このあと、同席した人に「昨日structlogのトークしてたよね？」って声をかけられた。
devopsでログ取っててー、とのこと。
声をかけてもらえると嬉しい。スピーカー特権ですね。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id34&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-warroom-working.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-warroom-working.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-warroom-working.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;War Room でトーク準備中の武居さん&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;2日目のトーク直前まで準備に余念が無い
（私はトークは1日目の方がうれしい..気が落ち着かないので）&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id35&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-icecream-vendor.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-icecream-vendor.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-icecream-vendor.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントの無料アイス&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;フィリピン人はアイス好き（という印象）
主催メンバーに「あの無料アイスは何？」と聞いたら、サプライズで用意したとのこと。
コーヒーは高くて無料にてきなかったけど、アイスはできたらしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id36&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-icecream-takei.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-icecream-takei.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-icecream-takei.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;「この年になってもまだ挑戦できる」&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;と、英語トーク初登壇をやり遂げた武居さん。
「一仕事終えた後のアイス美味しい。」&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id37&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-taho.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-taho.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-taho.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントの無料タホ&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;アイス屋さんが “タホ” も配ってました。&lt;/p&gt;
&lt;p&gt;「タホ」はタガログ語で「豆腐」。
温かい豆腐、サゴ（タピオカぽい）、黒蜜をカップに入れてくれる&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id38&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-snack-pizza.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-snack-pizza.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-snack-pizza.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;イベントおやつ2: ピザ&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;フィリピン人はピザも好き（という体感。イートインできるピザ屋が多め）&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id39&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-gathering.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-gathering.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-gathering.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;集合写真（後ろから）&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id40&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-elias-brewing.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-elias-brewing.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-elias-brewing.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;日本から参加したみなさん&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;イベント後に、Elias Wicked Ales &amp;amp; Spirits へGrabで移動。
醸造エリアに入れてくれたので、記念撮影しました。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id41&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-elias-menuboard.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-elias-menuboard.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-elias-menuboard.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;クラフトビールのメニューボード&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;&lt;a class="reference external" href="https://untappd.com/"&gt;Untapped&lt;/a&gt; でチェックインするとメニューボードに人が表示されて、楽しい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id42&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-elias-shrimp.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-elias-shrimp.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-elias-shrimp.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;SHRIMP GAMBAS（エビのガンバス）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;海老のピリ辛炒め。味は濃い。
Philippinesの料理らしい。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id43&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-elias-sisig.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-elias-sisig.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-elias-sisig.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Sisig（シシグ）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;Philippinesの伝統料理。
豚コマをしょう油、 酢、にんにく、唐辛子で炒め。味は濃い。
これは辛くなかった。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id44&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day2-elias-streetfood.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day2-elias-streetfood.jpg" src="https://www.freia.jp/taka/_images/ph2025-day2-elias-streetfood.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;ストリートフード大皿（内訳不明）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;おでんの具っぽい串、えびせん、イカ？&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;イベント翌日。&lt;/p&gt;
&lt;figure class=align-default id=id45&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/ph2025-day3-fruitas.jpg"&gt;&lt;img alt="../../../../_images/ph2025-day3-fruitas.jpg" src="https://www.freia.jp/taka/_images/ph2025-day3-fruitas.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Fruitas のブコジュース（ココナッツジュース）&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;ココナッツジュースはこれ一択（生ココナッツを除く）。
空港の制限エリアで1本100ペソ（300円）だったので2本買って帰りました。
ちなみに、街では75ペソだったと思う。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;おしまい。&lt;/p&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Thu, 27 Mar 2025 06:30:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/03/pyconapac2025/index.html</guid></item><item><title>PyCon mini Shizuoka 2024 Continue に参加しました</title><link>https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html</link><description>&lt;section id=pycon-mini-shizuoka-2024-continue&gt;

&lt;p&gt;2月8日に静岡市で開催された、PyCon mini Shizuoka 2024 Continue に参加しました。
PyCon mini Shizuoka での、現地初開催のイベントです。&lt;/p&gt;
&lt;p&gt;現地開催の企画が2回あり、2020年はコロナ禍でオンラインに切り替え、2024年8月には台風で延期となり、ついに今回 &lt;strong&gt;2024 Continue&lt;/strong&gt; として開催されました。私も現地でキーノート発表させていただき、感慨深いイベントとなりました。&lt;/p&gt;
&lt;figure class=align-default id=id13&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/group-photo.jpg"&gt;&lt;img alt="../../../../_images/group-photo.jpg" src="https://www.freia.jp/taka/_images/group-photo.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;Photo by sano hiroshi&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;参加人数はconnpass上で52名（スタッフ含む？）、キーノート + パネル、2トラックで10トーク、LT、と盛りだくさんなイベントでした。&lt;/p&gt;
&lt;section id=id1&gt;
&lt;h2&gt;イベント概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;イベント名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;PyCon mini Shizuoka 2024 Continue&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;公式ウェブサイト&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://shizuoka.pycon.jp/2024-continue/"&gt;https://shizuoka.pycon.jp/2024-continue/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;発表資料&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;&lt;a class="reference external" href="https://pycon-shizu.connpass.com/event/337283/presentation/"&gt;https://pycon-shizu.connpass.com/event/337283/presentation/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;日付&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;2025年2月8日(土)&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;場所&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;静岡市コ・クリエーションスペース &amp;amp; B-nest&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;参加費&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;無料&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;p&gt;私の参加時のメモ（blog元ネタ）が &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2024"&gt;PyCon mini Shizuoka 2024 - 清水川のScrapbox&lt;/a&gt; にあります。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id2&gt;
&lt;h2&gt;開場～オープニング&lt;/h2&gt;
&lt;p&gt;会場は静岡駅から徒歩10分ほどの &lt;a class="reference external" href="https://coc-shizuoka.jp/"&gt;静岡市 コ・クリエーションスペース&lt;/a&gt; 。登録すると無料で利用できるそうです。WiFiもあるし有り難い。&lt;/p&gt;
&lt;figure class=align-default id=id14&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/venue1.jpg"&gt;&lt;img alt="../../../../_images/venue1.jpg" src="https://www.freia.jp/taka/_images/venue1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;&lt;a class="reference external" href="https://coc-shizuoka.jp/"&gt;静岡市 コ・クリエーションスペース&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;受付は &lt;a class="reference external" href="https://help.connpass.com/topics/event-attendee-qr-checkin"&gt;ConnpassのQRコード&lt;/a&gt; を使って、名札カードに手書きで名前を書くスタイル。
QRコード受付は手軽で良いですね。&lt;/p&gt;
&lt;figure class=align-default id=id15&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/reception2.jpg"&gt;&lt;img alt="../../../../_images/reception2.jpg" src="https://www.freia.jp/taka/_images/reception2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;会場入り口で受付。静岡おでんがお出迎え…?&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id16&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/room.jpg"&gt;&lt;img alt="../../../../_images/room.jpg" src="https://www.freia.jp/taka/_images/room.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;部屋名が「テントサイト」らしい&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;10時の開場に合わせて行ったんですが、ここでキーノート用に用意したイベントTシャツを着忘れたことに気付いて、慌ててホテルまでダッシュで往復しました。&lt;/p&gt;
&lt;p&gt;10時半からのオープニングには間に合った。よかった…。&lt;/p&gt;
&lt;figure class=align-default id=id17&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/opening01.jpg"&gt;&lt;img alt="../../../../_images/opening01.jpg" src="https://www.freia.jp/taka/_images/opening01.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オープニングトークを行う、座長の佐野さん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id4&gt;
&lt;h2&gt;キーノート と パネル&lt;/h2&gt;
&lt;p&gt;オープニングのあと、午前中はキーノートとコミュニティーパネルで連続登壇させていただきました。&lt;/p&gt;
&lt;figure class=align-default id=id18&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/keynote1.jpg"&gt;&lt;img alt="../../../../_images/keynote1.jpg" src="https://www.freia.jp/taka/_images/keynote1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;"未知との出会い" by 私&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;ul class=simple&gt;
&lt;li&gt;&lt;p&gt;Photo by &lt;a class="reference external" href="https://x.com/takanory/status/1888042097909055682"&gt;https://x.com/takanory/status/1888042097909055682&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;スライド: &lt;a class="reference external" href="https://freia.jp/taka/slides/pyconshizu2024/"&gt;https://freia.jp/taka/slides/pyconshizu2024/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;おまけのRevealJS版: &lt;a class="reference external" href="https://freia.jp/taka/slides/pyconshizu2024/r/"&gt;https://freia.jp/taka/slides/pyconshizu2024/r/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;キーノートは「未知との出会い」と題して、未知と出会えるプログラミング、そしてイベント参加は楽しいよ、という話をさせて頂きました。参加いただいたみなさん、ありがとうございました！&lt;/p&gt;
&lt;p&gt;内容について自分で解説するのもアレなので、ここでは裏話をすこし紹介します。今回のキーノートについて参加された方からは「面白かった」という好評をいただきましたが、2024年8月に予定していたキーノート内容はこれに比べるとだいぶ未完成だったなと思います。あらすじは変えていませんが、表現方法はまったく変わっていて、Pyxel &lt;a class="footnote-reference brackets" href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html#id7" id=id5 role=doc-noteref&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;1&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/a&gt; でプレゼンテーションツールを作り、そこにPyxel製ゲームをPinP（Pyxel in Pyxel）で埋め込んで実際に操作できるようにしました。&lt;/p&gt;
&lt;p&gt;プレゼンツールを作ったことで、キーノート中にスライドの中でタイピングゲームしたり、WebSocketサーバーを介して参加者と一緒に多人数操作したりを交えつつ進めることが出来るようになりました。はじめは単に添え物としてゲームを作り始めましたが、ふと、スライドもPyxelで作れるんじゃないかと思い実装しました。原稿ソースの読み込みと、ビジターパターンを使った描画はなんどか実装したことがあるので、表示自体は比較的簡単でした（Sphinxコミッターとして活動していた経験がここで役立ちました）。その延長で、Pyxelゲームを埋め込めることに気付いてやってみたら出来た感じです &lt;a class="footnote-reference brackets" href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html#id8" id=id6 role=doc-noteref&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;2&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/a&gt; 。操作感と原稿ソースの記法は &lt;a class="reference external" href="https://attakei.github.io/sphinx-revealjs/ja/"&gt;sphinx-revealjs&lt;/a&gt; 互換を目指しました。&lt;/p&gt;
&lt;p&gt;プレゼンツールとPinP用アプリ5つを &lt;a class="reference external" href="https://github.com/shimizukawa/pyxel-app/commits/master/03-slide?after=42cf973e51987089c5b965dc813e606ac5692c82+34"&gt;3週間くらいで実装&lt;/a&gt; しています。並行してプレゼン原稿の用意を行いましたが、Pyxelで作ると決めてからは時間内にどれだけアイディアを実装できるかの勝負という感じで、めちゃくちゃ楽しくプログラミングしていました。途中、この方向性で面白いのかを確認したくて &lt;a class="reference external" href="https://sphinxjp.connpass.com/"&gt;Sphinx+翻訳 Hack-a-thon&lt;/a&gt; では多人数操作やSlide表示のデモをして、好意的なフィードバックをもらえたことで開発の勢いを付けられたし、新しい発想を得て盛り込めたと思います。最後、本番環境でWebSocketが動いたのが本番前日の26時でしたが、こういう時は楽しくてとても充実した気持ちのまま本番トークに臨むことが出来ました。&lt;/p&gt;
&lt;p&gt;キーノートで頂いた質問と回答、あとパネルでの会話は、 &lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2024"&gt;PyCon mini Shizuoka 2024 - 清水川のScrapbox&lt;/a&gt; にメモしました。改めて、当日参加いただいたみなさん、そして実装デモにお付き合い頂いたSphinx+翻訳 Hack-a-thonのみなさん、ありがとうございました！&lt;/p&gt;
&lt;p&gt;--&lt;/p&gt;
&lt;aside class="footnote-list brackets"&gt;
&lt;aside class="footnote brackets" id=id7 role=doc-footnote&gt;
&lt;span class=label&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;&lt;a href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html#id5" role=doc-backlink&gt;1&lt;/a&gt;&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;&lt;a class="reference external" href="https://github.com/kitao/pyxel/blob/main/docs/README.ja.md"&gt;Pyxel&lt;/a&gt; はPython用レトロゲームエンジン。エンジン自体の実装はRust。メタルギアソリッド等のゲーム開発に携わった北尾さんが開発しています。 &lt;a class="reference external" href="https://levtech.jp/media/article/focus/detail_573/"&gt;『メタルギア』『ZOE』の開発者がレトロゲームエンジン「Pyxel」を作った理由【フォーカス】 | レバテックラボ（レバテックLAB）&lt;/a&gt; が良い記事でした。&lt;/p&gt;
&lt;/aside&gt;
&lt;aside class="footnote brackets" id=id8 role=doc-footnote&gt;
&lt;span class=label&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;&lt;a href="https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html#id6" role=doc-backlink&gt;2&lt;/a&gt;&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;Pyxelスライドアプリのソースコードは &lt;a class="reference external" href="https://github.com/shimizukawa/pyxel-app/tree/master/03-slide"&gt;https://github.com/shimizukawa/pyxel-app/tree/master/03-slide&lt;/a&gt; にあります。キーノートのコードは公開予定ありませんが、アーキテクチャ紹介はどこかで機会があればやりたいな。&lt;/p&gt;
&lt;/aside&gt;
&lt;/aside&gt;
&lt;/section&gt;
&lt;section id=id10&gt;
&lt;h2&gt;ランチ&lt;/h2&gt;
&lt;p&gt;ランチは各自出かけて近所で食べる方式でした。静岡といえば「しぞーかおでん」と言うことで、静岡駅の「海ぼうず」というお店に5人で行って、おでんを頂きました。&lt;/p&gt;
&lt;figure class=align-default id=id19&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/oden1.jpg"&gt;&lt;img alt="../../../../_images/oden1.jpg" src="https://www.freia.jp/taka/_images/oden1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;海ぼうず&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;figure class=align-default id=id20&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/oden2.jpg"&gt;&lt;img alt="../../../../_images/oden2.jpg" src="https://www.freia.jp/taka/_images/oden2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;静岡B級グルメセット 1800円。&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;しぞーかおでん、みしまコロッケ、カレー？、とちょっとボリュームありすぎ！だけど美味しかった。静岡（東部）には何度も来ているけど、こんなおでん食べたことなかったなー。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=lt&gt;
&lt;h2&gt;トーク &amp;amp; LT&lt;/h2&gt;
&lt;p&gt;&lt;a class="reference external" href="https://scrapbox.io/shimizukawa/PyCon_mini_Shizuoka_2024"&gt;PyCon mini Shizuoka 2024 - 清水川のScrapbox&lt;/a&gt; に、キーノートを含む、各トーク、LTのメモや質疑応答、写真をまとめました。&lt;/p&gt;
&lt;p&gt;今回のイベントは2トラックだったのですが、ずっとテントサイト（ルーム1）の同じ席でトークを聞いていました。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id11&gt;
&lt;h2&gt;クロージング ～ 懇親会&lt;/h2&gt;
&lt;figure class=align-default id=id21&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/closing1.jpg"&gt;&lt;img alt="../../../../_images/closing1.jpg" src="https://www.freia.jp/taka/_images/closing1.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;クロージング、静岡スタッフ勢揃い&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;イベント運営スタッフのみなさん、ありがとうございました！&lt;/p&gt;
&lt;p&gt;そして、PyCon mini 東海 2025 の開催宣言！11月頃に開催予定とのこと。&lt;/p&gt;
&lt;figure class=align-default id=id22&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/tokai2025.jpg"&gt;&lt;img alt="../../../../_images/tokai2025.jpg" src="https://www.freia.jp/taka/_images/tokai2025.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;東海スタッフのみなさん&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;懇親会は、 &lt;a class="reference external" href="https://nadh500.gorp.jp/"&gt;GROW STOCK&lt;/a&gt; というクラフトビールのお店。ビールも料理も美味しかった。
クラフトビールの名前「賎機IPA」「駿府アルト」は読めなかったよ。静岡の地名だそうです。&lt;/p&gt;
&lt;figure class=align-default id=id23&gt;
&lt;a class="reference internal image-reference" href="https://www.freia.jp/taka/_images/party2.jpg"&gt;&lt;img alt="../../../../_images/party2.jpg" src="https://www.freia.jp/taka/_images/party2.jpg" style="width: 80%;"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;かんぱい！&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;section id=id12&gt;
&lt;h2&gt;感想&lt;/h2&gt;
&lt;p&gt;楽しかった、というのもありつつ、個人的には「やりきった」という感じでした。
延期になってから6ヶ月の間、一番伝えたい事は何かを考え続けて、凝縮させられたと思います。&lt;/p&gt;
&lt;p&gt;また、今回のイベントで出会った多くの人からも刺激をもらえました。運営されたみなさん、参加されたみなさん、ありがとうございました！&lt;/p&gt;
&lt;p&gt;おまけ&lt;/p&gt;
&lt;figure class=align-default id=id24&gt;
&lt;img alt="../../../../_images/wcb.jpg" src="https://www.freia.jp/taka/_images/wcb.jpg"&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;2022年9月23日。塚本さんと &lt;a class="reference external" href="https://www.westcoastbrewing.jp/location/12-twelve/"&gt;12 - twelve&lt;/a&gt; にて。&lt;/span&gt;&lt;/p&gt;
&lt;div class=legend&gt;
&lt;p&gt;静岡駅前のWest Coast Breawing直営店でビールを飲んでたら、たまたま塚本さんが近くにいてお店に来てくれて、ここでキーノートの打診を頂きました。それから2年半。フィリピンに転居したり、台風に狙い撃ちされたり、色々ありました。&lt;/p&gt;
&lt;/div&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Fri, 14 Feb 2025 13:30:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/02/pyconshizuoka2024/index.html</guid></item><item><title>書籍紹介: 『＃100日チャレンジ』プログラミング x ChatGPTで&amp;quot;自分だけのHACK&amp;quot;を見つけた挑戦譚</title><link>https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html</link><description>&lt;section id=x-chatgpt-hack&gt;

&lt;figure class=align-default id=id10&gt;
&lt;a class="reference external image-reference" href="https://amzn.to/4iTGUIJ"&gt;&lt;img alt="../../../../_images/book-b.jpg" src="https://www.freia.jp/taka/_images/book-b.jpg"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;&lt;a class="reference external" href="https://amzn.to/4iTGUIJ"&gt;＃100日チャレンジ 毎日連続100本アプリを作ったら人生が変わった&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;本書は、大学4年生が「宿題をサボるため」にChatGPTを活用して、それをきっかけに「＃100日チャレンジ」で毎日1本ずつアプリを作り続ける話です。編集者さんから年末に恵贈頂き、スキマ時間で読もうかなと思ったら、予想外に面白くてほぼ1日で読み終わってしまいました。&lt;/p&gt;
&lt;section id=id2&gt;
&lt;h2&gt;学習探求というより、冒険譚&lt;/h2&gt;
&lt;p&gt;本書の面白さは、ChatGPTを"宿題回避ツール"として使い始めたはずの「怠惰」な著者が、いつしか「作品作りの主体は私だ！」と意識を変化させていく心情の変化のプロセスが描かれている所にあると思います。編集者さんからは "PythonプログラミングをChatGPTで学んだ大学生の「AI駆動型プログラミング学習探究記」の本" と紹介頂いていましたが、私は本書を学習探究というより、 &lt;strong&gt;プログラミングとChatGPTを題材にした冒険譚&lt;/strong&gt; だと思いました。プログラミング教育のセオリーとか常識を完全無視で進んでいくあたりは異世界転生もの &lt;a class="footnote-reference brackets" href="https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html#id6" id=id3 role=doc-noteref&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;1&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/a&gt; っぽい感じもします。&lt;/p&gt;
&lt;figure class=align-default id=id11&gt;
&lt;a class="reference external image-reference" href="https://amzn.to/4iTGUIJ"&gt;&lt;img alt="../../../../_images/book-ura.jpg" src="https://www.freia.jp/taka/_images/book-ura.jpg"&gt;
&lt;/a&gt;
&lt;figcaption&gt;
&lt;p&gt;&lt;span class=caption-text&gt;オビの背表紙側に、心情変化が綴られているのが目を惹く&lt;/span&gt;&lt;/p&gt;
&lt;/figcaption&gt;
&lt;/figure&gt;
&lt;p&gt;オビには「オセロを作って! 」と指示しているように書いていますが、実際には関数を1つずつ生成させるプロンプトで指示した、という話が &lt;a class="reference external" href="https://ascii.jp/elem/000/004/185/4185964/"&gt;ASCII.jp：女子大生が100日連続で生成AIで100本のプログラムを書いたらどうなったか？&lt;/a&gt; で紹介されていました（この記事も超長いけど面白い）。書籍内でもChatGPTとの付き合い方の変遷が描かれていて、実践しているからこそのリアリティがあります（って言うか実話でしたね）。&lt;/p&gt;
&lt;p&gt;文章も読みやすく、初めての執筆とは思えませんでした。なので「執筆もChatGPTにやってもらったのかな」と思ったら、執筆時にはAI使用禁止が厳命 &lt;a class="footnote-reference brackets" href="https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html#id9" id=id4 role=doc-noteref&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;2&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/a&gt; されていたらしく、執筆のためにイチから書き方や物語の構成を学び、習得したスキルをフル活用して書き上げたそうです。まるで「目的に合わせたスキル獲得を最短ルートで行う方法を見出す才能」を持っているかのようです。マジかよ…すごい。&lt;/p&gt;
&lt;p&gt;プログラミング初心者の方はもちろん、色々な人に刺激になる、お勧めの1冊だと思います。&lt;/p&gt;
&lt;/section&gt;
&lt;section id=id5&gt;
&lt;h2&gt;書籍概要&lt;/h2&gt;
&lt;dl class="field-list simple"&gt;
&lt;dt class=field-odd&gt;書籍名&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;＃100日チャレンジ 毎日連続100本アプリを作ったら人生が変わった&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;出版社&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;日経BP&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;著者&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;大塚あみ (著)&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;ページ数&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;224&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;金額&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;1800円+税&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;発売時期&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;2025/01/11&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-odd&gt;出版社リンク&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-odd&gt;&lt;p&gt;&lt;a class="reference external" href="https://bookplus.nikkei.com/atcl/catalog/24/12/05/01757/"&gt;https://bookplus.nikkei.com/atcl/catalog/24/12/05/01757/&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;dt class=field-even&gt;Amazonリンク&lt;span class=colon&gt;:&lt;/span&gt;&lt;/dt&gt;
&lt;dd class=field-even&gt;&lt;p&gt;&lt;a class="reference external" href="https://amzn.to/4iTGUIJ"&gt;https://amzn.to/4iTGUIJ&lt;/a&gt;&lt;/p&gt;
&lt;/dd&gt;
&lt;/dl&gt;
&lt;aside class="footnote-list brackets"&gt;
&lt;aside class="footnote brackets" id=id6 role=doc-footnote&gt;
&lt;span class=label&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;&lt;a href="https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html#id3" role=doc-backlink&gt;1&lt;/a&gt;&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;その世界の既成概念に囚われずに能力を発揮する感じが、異世界転生ものっぽい、かな。 &lt;a class="reference external" href="https://amzn.to/3C8ZfAH"&gt;エルハザード&lt;/a&gt; とか、 &lt;a class="reference external" href="https://amzn.to/4gKioZ0"&gt;日帰りクエスト&lt;/a&gt; とか（古い）？最近のは知らないんですよね…。&lt;/p&gt;
&lt;/aside&gt;
&lt;aside class="footnote brackets" id=id9 role=doc-footnote&gt;
&lt;span class=label&gt;&lt;span class=fn-bracket&gt;[&lt;/span&gt;&lt;a href="https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html#id4" role=doc-backlink&gt;2&lt;/a&gt;&lt;span class=fn-bracket&gt;]&lt;/span&gt;&lt;/span&gt;
&lt;p&gt;編集者さんから聞きました。執筆者ご本人も &lt;a class="reference external" href="https://note.com/amiotsuka/n/nda94c4fa32cf"&gt;それは、レポート課題をAIにやらせようとしたことから始まった。｜Ami&lt;/a&gt; で言及されています&lt;/p&gt;
&lt;/aside&gt;
&lt;/aside&gt;
&lt;/section&gt;
&lt;/section&gt;
</description><pubDate>Wed, 08 Jan 2025 19:00:00 -0000</pubDate><guid>https://www.freia.jp/taka/blog/2025/01/100-days-challenge/index.html</guid></item></channel></rss>