<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Python | Tomokatsu Yukishita | yre.jp</title><link>https://yre.jp/tag/python/</link><atom:link href="https://yre.jp/tag/python/index.xml" rel="self" type="application/rss+xml"/><description>Python</description><generator>Hugo Blox Builder (https://hugoblox.com)</generator><language>ja-JP</language><lastBuildDate>Tue, 19 Jul 2022 00:00:00 +0000</lastBuildDate><image><url>https://yre.jp/media/icon_hufbc159bd6ce6a866189b19a79c0d0f51_12846_512x512_fill_lanczos_center_3.png</url><title>Python</title><link>https://yre.jp/tag/python/</link></image><item><title>Raspberry Pi + CO2-mini + Zabbixで室内CO2濃度を継続モニタリングする構築手順</title><link>https://yre.jp/post/co2-mini/</link><pubDate>Tue, 19 Jul 2022 00:00:00 +0000</pubDate><guid>https://yre.jp/post/co2-mini/</guid><description>&lt;p>コロナ禍をきっかけにCO2モニター「CUSTOM CO2-mini」を購入しました。USB給電で動作するこのセンサー、調べてみるとUSB経由でデータ取得もできることが判明。Raspberry Piに接続してZabbixで継続的に室内CO2濃度をモニタリングする仕組みを作ったので、構築手順をまとめます。&lt;/p>
&lt;h2 id="用意するもの">用意するもの&lt;/h2>
&lt;h3 id="raspberry-pi">Raspberry Pi&lt;/h3>
&lt;a href="https://www.amazon.co.jp/dp/B081YD3VL5?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/51ETv8Le3nL._AC_.jpg" alt="【国内正規代理店品】Raspberry Pi4 ModelB 4GB ラズベリーパイ4 技適対応品">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">【国内正規代理店品】Raspberry Pi4 ModelB 4GB ラズベリーパイ4 技適対応品&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="co2-minicustom-co2モニター">CO2-mini（CUSTOM CO2モニター）&lt;/h3>
&lt;a href="https://www.amazon.co.jp/dp/B00I3XJ9LM?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/31zFBrDz0-L._SL1000_.jpg" alt="カスタム (CUSTOM) CO2モニター CO2-mini">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">カスタム (CUSTOM) CO2モニター CO2-mini&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="電源microsdカード">電源・microSDカード&lt;/h3>
&lt;a href="https://www.amazon.co.jp/dp/B07DN5V3VN?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/61Iaz4sqdaS._AC_SL1500_.jpg" alt="Smraza Raspberry Pi 4 USB-C電源 5V 3A（ON/OFFスイッチ付き）">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">Smraza Raspberry Pi 4 USB-C電源 5V 3A（ON/OFFスイッチ付き）&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;a href="https://amzn.to/4bF8t5G" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/61&amp;#43;B0wJtRFL._AC_SL1500_.jpg" alt="SanDisk microSD カード 128GB UHS-I U1 Class10">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">SanDisk microSD カード 128GB UHS-I U1 Class10&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h2 id="co2-miniからのデータ取得python">CO2-miniからのデータ取得（Python）&lt;/h2>
&lt;p>CO2-miniをRaspberry PiにUSB接続すると、特別なドライバーなしで認識されます。データ取得には &lt;a href="https://github.com/heinemml/CO2Meter" target="_blank" rel="noopener">heinemml/CO2Meter&lt;/a> というPythonライブラリを使います。&lt;/p>
&lt;h3 id="ライブラリのインストール">ライブラリのインストール&lt;/h3>
&lt;p>Raspberry Pi OS Bookworm 以降では、システムの Python に直接 pip インストールすることが制限されています。仮想環境を作成してその中にインストールします。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">python3 -m venv /root/co2env
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">/root/co2env/bin/pip install git+https://github.com/heinemml/CO2Meter
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;div class="alert alert-note">
&lt;div>
&lt;code>sudo pip3 install ...&lt;/code> は Raspberry Pi OS Bookworm（2023年以降）では &amp;ldquo;externally managed environment&amp;rdquo; エラーになる場合があります。仮想環境を使う手順が安全です。
&lt;/div>
&lt;/div>
&lt;h3 id="co2温度をshared-memoryに書き出すスクリプト">CO2・温度をShared Memoryに書き出すスクリプト&lt;/h3>
&lt;p>ZabbixエージェントからCO2値を読み取れるよう、取得した値を &lt;code>/dev/shm/&lt;/code> 以下のファイルに継続的に書き出します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-python" data-lang="python">&lt;span class="line">&lt;span class="cl">&lt;span class="kn">from&lt;/span> &lt;span class="nn">CO2Meter&lt;/span> &lt;span class="kn">import&lt;/span> &lt;span class="o">*&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kn">import&lt;/span> &lt;span class="nn">time&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="n">sensor&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="n">CO2Meter&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s2">&amp;#34;/dev/hidraw0&amp;#34;&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="c1"># 環境によって hidraw1 などになる場合があります&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="k">while&lt;/span> &lt;span class="kc">True&lt;/span>&lt;span class="p">:&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="n">time&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">sleep&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="mi">1&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="n">data&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="n">sensor&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">get_data&lt;/span>&lt;span class="p">()&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">if&lt;/span> &lt;span class="s1">&amp;#39;temperature&amp;#39;&lt;/span> &lt;span class="ow">in&lt;/span> &lt;span class="n">data&lt;/span> &lt;span class="ow">and&lt;/span> &lt;span class="s1">&amp;#39;co2&amp;#39;&lt;/span> &lt;span class="ow">in&lt;/span> &lt;span class="n">data&lt;/span>&lt;span class="p">:&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">with&lt;/span> &lt;span class="nb">open&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s1">&amp;#39;/dev/shm/co2&amp;#39;&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="s1">&amp;#39;w&amp;#39;&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="k">as&lt;/span> &lt;span class="n">f&lt;/span>&lt;span class="p">:&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="n">f&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">write&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nb">str&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="n">data&lt;/span>&lt;span class="p">[&lt;/span>&lt;span class="s1">&amp;#39;co2&amp;#39;&lt;/span>&lt;span class="p">]))&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">with&lt;/span> &lt;span class="nb">open&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s1">&amp;#39;/dev/shm/temperature&amp;#39;&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="s1">&amp;#39;w&amp;#39;&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="k">as&lt;/span> &lt;span class="n">f&lt;/span>&lt;span class="p">:&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="n">f&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">write&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nb">str&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="n">data&lt;/span>&lt;span class="p">[&lt;/span>&lt;span class="s1">&amp;#39;temperature&amp;#39;&lt;/span>&lt;span class="p">]))&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;div class="alert alert-note">
&lt;div>
&lt;code>/dev/hidraw0&lt;/code> のデバイスパスは環境によって異なります。&lt;code>ls /dev/hidraw*&lt;/code> で確認し、CO2-miniが認識されているパスを指定してください。
&lt;/div>
&lt;/div>
&lt;h3 id="起動時に自動実行するcrontab">起動時に自動実行する（crontab）&lt;/h3>
&lt;p>rootでないとデバイスにアクセスできないため、root権限で起動するシェルスクリプトを作成します。&lt;/p>
&lt;p>&lt;code>/root/co2.sh&lt;/code>&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">&lt;span class="cp">#!/bin/bash
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="cp">&lt;/span>sleep &lt;span class="m">5&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">/root/co2env/bin/python3 /root/co2.py
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>crontabに追加して起動時に自動実行するよう設定します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">@reboot /root/co2.sh
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="zabbixの設定">Zabbixの設定&lt;/h2>
&lt;p>ZabbixからRaspberry Piのデータを収集するには、zabbix-serverとzabbix-agentの両方を設定する必要があります。&lt;/p>
&lt;h3 id="方針">方針&lt;/h3>
&lt;ul>
&lt;li>Raspberry PiのShared Memory（&lt;code>/dev/shm/&lt;/code>）にCO2値と温度を常時書き出す&lt;/li>
&lt;li>Zabbixエージェントはそのファイルを &lt;code>cat&lt;/code> して返す&lt;/li>
&lt;/ul>
&lt;h3 id="zabbix-server側ホストとアイテムの作成">zabbix-server側：ホストとアイテムの作成&lt;/h3>
&lt;p>Raspberry Piにzabbix-agentをインストールし、zabbix-serverでホストを追加します。&lt;/p>
&lt;p>
&lt;figure id="figure-zabbixでホストを作成する">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="Zabbixのホスト作成画面。Raspberry PiのIPアドレスを指定してホストを追加している様子" srcset="
/media/co2-mini/da06e12e47b74a91077c01cd16525293_hu313760b14cba40592b4c4bfe8a53f596_72911_1b1d6d1894adc4b8bbffecf8e53f3544.webp 400w,
/media/co2-mini/da06e12e47b74a91077c01cd16525293_hu313760b14cba40592b4c4bfe8a53f596_72911_fea422ab79f99abf87bd10e92c424003.webp 760w,
/media/co2-mini/da06e12e47b74a91077c01cd16525293_hu313760b14cba40592b4c4bfe8a53f596_72911_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/co2-mini/da06e12e47b74a91077c01cd16525293_hu313760b14cba40592b4c4bfe8a53f596_72911_1b1d6d1894adc4b8bbffecf8e53f3544.webp"
width="760"
height="196"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
Zabbixでホストを作成する
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>CO2濃度と温度の2つのアイテムを作成します。&lt;/p>
&lt;p>
&lt;figure id="figure-co2濃度と温度のアイテムを作成する">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="ZabbixのアイテムリストにCO2濃度と温度の2つのアイテムが表示されている画面" srcset="
/media/co2-mini/5ce5e9a101dc3a9f247f663aa8f0a7b3_hud28ccdbdbed7334ddc3ee0b604058f9a_103897_9c11300127e1612b7ef1f8456817bccb.webp 400w,
/media/co2-mini/5ce5e9a101dc3a9f247f663aa8f0a7b3_hud28ccdbdbed7334ddc3ee0b604058f9a_103897_90cd0f3739ec77d7e841d665277f56f1.webp 760w,
/media/co2-mini/5ce5e9a101dc3a9f247f663aa8f0a7b3_hud28ccdbdbed7334ddc3ee0b604058f9a_103897_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/co2-mini/5ce5e9a101dc3a9f247f663aa8f0a7b3_hud28ccdbdbed7334ddc3ee0b604058f9a_103897_9c11300127e1612b7ef1f8456817bccb.webp"
width="760"
height="608"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
CO2濃度と温度のアイテムを作成する
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>
&lt;figure id="figure-アイテムのキー設定userparameterと対応させる">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="ZabbixのアイテムキーにUserParameter名（co2.co2 / co2.temp）を設定している設定画面" srcset="
/media/co2-mini/9017e828e3c4efcae08dca0091351baa-1024x819_hu8f2faefe9ab31af6c31fc87aa0f0d22a_115242_3294bf3e25f8357036b10c044d045648.webp 400w,
/media/co2-mini/9017e828e3c4efcae08dca0091351baa-1024x819_hu8f2faefe9ab31af6c31fc87aa0f0d22a_115242_e4cb036ba6e841d0d2fb0d635f2939e1.webp 760w,
/media/co2-mini/9017e828e3c4efcae08dca0091351baa-1024x819_hu8f2faefe9ab31af6c31fc87aa0f0d22a_115242_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/co2-mini/9017e828e3c4efcae08dca0091351baa-1024x819_hu8f2faefe9ab31af6c31fc87aa0f0d22a_115242_3294bf3e25f8357036b10c044d045648.webp"
width="760"
height="608"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
アイテムのキー設定（UserParameterと対応させる）
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>アイテムキーは以下にしました。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="cl">co2.co2 （CO2濃度）
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">co2.temp （温度）
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="zabbix-agent側設定ファイルの編集">zabbix-agent側：設定ファイルの編集&lt;/h3>
&lt;p>&lt;code>/etc/zabbix/zabbix_agentd.conf&lt;/code> でサーバーアドレスを指定します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="cl">Server=&amp;lt;zabbix-serverのアドレス&amp;gt;
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">ServerActive=&amp;lt;zabbix-serverのアドレス&amp;gt;
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Include=/etc/zabbix/zabbix_agentd.conf.d/*.conf
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="userparameterの設定">UserParameterの設定&lt;/h3>
&lt;p>&lt;code>/etc/zabbix/zabbix_agentd.conf.d/userparameter_co2.conf&lt;/code> を作成します。Shared Memoryのファイルを &lt;code>cat&lt;/code> して返すだけです。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="cl">UserParameter=co2.co2,cat /dev/shm/co2
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">UserParameter=co2.temp,cat /dev/shm/temperature
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>設定後、zabbix-agentを再起動します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">sudo systemctl restart zabbix-agent
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="動作結果">動作結果&lt;/h2>
&lt;p>CO2濃度と温度をZabbixでグラフ化できました。&lt;/p>
&lt;p>
&lt;figure id="figure-co2濃度のzabbixグラフ換気のタイミングで値が下がるのがわかる">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="ZabbixのグラフにRaspberry Pi &amp;#43; CO2-miniで取得したCO2濃度のリアルタイムデータが折れ線グラフで表示されている" srcset="
/media/co2-mini/2f571cc59d7fa276e5cedf024f4227cf_hu277cd2d825a81d3f8ff9ed731bf6d1ea_117855_48a1d62b253931673888293d34fd422b.webp 400w,
/media/co2-mini/2f571cc59d7fa276e5cedf024f4227cf_hu277cd2d825a81d3f8ff9ed731bf6d1ea_117855_f0c054ecb0a4aa5844ee97e07d272a80.webp 760w,
/media/co2-mini/2f571cc59d7fa276e5cedf024f4227cf_hu277cd2d825a81d3f8ff9ed731bf6d1ea_117855_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/co2-mini/2f571cc59d7fa276e5cedf024f4227cf_hu277cd2d825a81d3f8ff9ed731bf6d1ea_117855_48a1d62b253931673888293d34fd422b.webp"
width="760"
height="165"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
CO2濃度のZabbixグラフ。換気のタイミングで値が下がるのがわかる
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>
&lt;figure id="figure-設置してからの長期推移冬は換気すると室温も下がるためco2上昇を許容しがち">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="Zabbixで数週間分のCO2濃度推移グラフ。冬季は窓を開けた後に急激にCO2が下がっている様子が見える" srcset="
/media/co2-mini/78ac805712a44e11300fa5ba4588254c_hu495835c02be0289c551a3002b397186b_290858_2cad7f32843dfd27d09684ba3e89f769.webp 400w,
/media/co2-mini/78ac805712a44e11300fa5ba4588254c_hu495835c02be0289c551a3002b397186b_290858_0a7ce34aa4d5b3be8bfd7327941efc86.webp 760w,
/media/co2-mini/78ac805712a44e11300fa5ba4588254c_hu495835c02be0289c551a3002b397186b_290858_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/co2-mini/78ac805712a44e11300fa5ba4588254c_hu495835c02be0289c551a3002b397186b_290858_2cad7f32843dfd27d09684ba3e89f769.webp"
width="760"
height="269"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
設置してからの長期推移。冬は換気すると室温も下がるため、CO2上昇を許容しがち
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>CO2モニターを導入してから、換気の頻度が体感でかなり上がりました。数値で見ると「換気が必要なタイミング」が一目瞭然です。&lt;/p>
&lt;h2 id="まとめ">まとめ&lt;/h2>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>構成要素&lt;/th>
&lt;th>役割&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>CO2-mini&lt;/td>
&lt;td>USB接続でCO2濃度・温度を計測&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Raspberry Pi&lt;/td>
&lt;td>センサーからデータを取得・Shared Memoryに保存&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Python（CO2Meterライブラリ）&lt;/td>
&lt;td>CO2-miniとの通信・データ取得&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Zabbix（agent + server）&lt;/td>
&lt;td>データの収集・グラフ化・長期記録&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;p>作成したスクリプト一式はGitHubで公開しています。&lt;/p>
&lt;p>&lt;a href="https://github.com/yukishita/co2-mini" target="_blank" rel="noopener">GitHub - yukishita/co2-mini：CUSTOM CO2-miniをZabbixで記録するプログラム&lt;/a>&lt;/p></description></item><item><title>Raspberry Pi + Google Drive でクラウド対応フォトフレームを自作する【rclone + fbi + Python】</title><link>https://yre.jp/post/raspi-photoframe/</link><pubDate>Tue, 19 Jul 2022 00:00:00 +0000</pubDate><guid>https://yre.jp/post/raspi-photoframe/</guid><description>&lt;p>写真が趣味で、2003年からデジタル一眼を使い始めて今に至ります。気づけば総撮影枚数は388,524枚。これだけ撮り溜めた写真を、スライドショー形式でリビングに飾りたいと思っていました。&lt;/p>
&lt;h2 id="市販のデジタルフォトフレームでは解決できなかった問題">市販のデジタルフォトフレームでは解決できなかった問題&lt;/h2>
&lt;p>市販のフォトフレームは、SDカードやUSBメモリにデータを入れて表示する仕組みが主流です。7〜10インチのものが多く、Amazonのランキングでも選択肢は豊富にあります。&lt;/p>
&lt;p>ただ、週1ペースで写真を撮り続ける身としては**「毎回SDカードに写真を入れ直す」運用が億劫**で、すぐに使わなくなりそうでした。&lt;/p>
&lt;p>
&lt;figure id="figure-クラウドから自動で写真を取得するフォトフレームのイメージ">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="Google DriveとRaspberry Piを組み合わせたクラウド対応フォトフレームのシステム構成図。クラウドから写真を自動取得してスライドショー表示する仕組みを示している" srcset="
/media/raspi-photoframe/5621deba8a18b839c7a4321764bb05e8_hub05f2d0d129c7ee7542169c2c963abde_86374_3f5a7eb7c7a059ffa19f361f5c9be38d.webp 400w,
/media/raspi-photoframe/5621deba8a18b839c7a4321764bb05e8_hub05f2d0d129c7ee7542169c2c963abde_86374_26bbc4e9cdb29660629bcf887c20be66.webp 760w,
/media/raspi-photoframe/5621deba8a18b839c7a4321764bb05e8_hub05f2d0d129c7ee7542169c2c963abde_86374_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/raspi-photoframe/5621deba8a18b839c7a4321764bb05e8_hub05f2d0d129c7ee7542169c2c963abde_86374_3f5a7eb7c7a059ffa19f361f5c9be38d.webp"
width="720"
height="405"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
クラウドから自動で写真を取得するフォトフレームのイメージ
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>Google Driveなどのクラウドストレージから自動で写真を取得して表示するフォトフレームが欲しかったのですが、市販品では見つからなかったため、自分で作ることにしました。&lt;/p>
&lt;h2 id="用意したもの">用意したもの&lt;/h2>
&lt;h3 id="raspberry-pi-4">Raspberry Pi 4&lt;/h3>
&lt;p>常時通電するフォトフレーム用途には、消費電力が低く小型なRaspberry Piが適しています。&lt;/p>
&lt;a href="https://www.amazon.co.jp/dp/B081YD3VL5?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/51ETv8Le3nL._AC_.jpg" alt="【国内正規代理店品】Raspberry Pi4 ModelB 4GB ラズベリーパイ4 技適対応品">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">【国内正規代理店品】Raspberry Pi4 ModelB 4GB ラズベリーパイ4 技適対応品&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="モバイルモニター">モバイルモニター&lt;/h3>
&lt;p>写真を表示するためのモニターです。FullHD・IPSパネルのモバイルモニターを選びました。市販のフォトフレームは視野角が狭いパネルが多いですが、パーツを自分で選べるのが自作の醍醐味です。モバイルモニターは電源が小型で設置の自由度も高いです。&lt;/p>
&lt;a href="https://amzn.to/4sgZdM5" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/71lbYPykVrL._AC_SL1500_.jpg" alt="モバイルモニター 15.6インチ タッチパネル モバイルディスプレイ">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">モバイルモニター 15.6インチ タッチパネル モバイルディスプレイ&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="microsdカード電源">microSDカード・電源&lt;/h3>
&lt;a href="https://amzn.to/4smVEnt" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/615exWhvZ0L._AC_SL1200_.jpg" alt="SanDisk 高耐久 ドライブレコーダー アクションカメラ対応 microSDHC 32GB">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">SanDisk 高耐久 ドライブレコーダー アクションカメラ対応 microSDHC 32GB&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;a href="https://www.amazon.co.jp/dp/B087CF6127?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/61W8QsDXSYL._AC_SL1500_.jpg" alt="Miuzei Raspberry Pi 4 電源 USB-C 5.1V 3A スイッチ付き PSE認証">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">Miuzei Raspberry Pi 4 電源 USB-C 5.1V 3A スイッチ付き PSE認証&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h2 id="システム構成">システム構成&lt;/h2>
&lt;h3 id="osraspberry-pi-os">OS：Raspberry Pi OS&lt;/h3>
&lt;p>&lt;a href="https://www.raspberrypi.com/software/" target="_blank" rel="noopener">Raspberry Pi OS&lt;/a> をSDカードに書き込んで使います。フォトフレーム用途なのでデスクトップ環境は不要で、CLIのみの Lite 版でセットアップします。&lt;/p>
&lt;h3 id="画像表示fbi">画像表示：fbi&lt;/h3>
&lt;p>CLIから直接フレームバッファに画像を表示できる &lt;code>fbi&lt;/code> を使います。以前はUbuntu上のGUIで動かすバージョンも作りましたが動作が不安定だったため、CLIベースの構成に切り替えました。&lt;/p>
&lt;h3 id="クラウドストレージとの連携rclone">クラウドストレージとの連携：rclone&lt;/h3>
&lt;p>&lt;a href="https://rclone.org" target="_blank" rel="noopener">rclone&lt;/a> を使ってGoogle Drive上の写真を定期的にダウンロードします。Google Drive以外にもDropbox・S3など70以上のクラウドサービスに対応しています。&lt;/p>
&lt;p>rcloneで写真をダウンロード → fbiでスライドショー表示、という流れです。&lt;/p>
&lt;h2 id="セットアップ">セットアップ&lt;/h2>
&lt;h3 id="raspberry-pi-os-のインストール">Raspberry Pi OS のインストール&lt;/h3>
&lt;p>Raspberry Pi Imager を使ってSDカードにイメージを書き込みます。&lt;/p>
&lt;p>
&lt;figure id="figure-raspberry-pi-imager-でosを書き込む">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="Raspberry Pi ImagerでmicroSDカードにRaspberry Pi OSを書き込んでいる画面。OSとストレージを選択してWRITEボタンを押す操作画面" srcset="
/media/raspi-photoframe/8ffcb7bfb32b5079533396b7542ed9a1_hu8982ae701f5d02b9ab9d1e54062b4b24_153362_fa36f9d2badcc15fd6500bcdc35fea83.webp 400w,
/media/raspi-photoframe/8ffcb7bfb32b5079533396b7542ed9a1_hu8982ae701f5d02b9ab9d1e54062b4b24_153362_5221b7fcaf02876b6223f09d17408d34.webp 760w,
/media/raspi-photoframe/8ffcb7bfb32b5079533396b7542ed9a1_hu8982ae701f5d02b9ab9d1e54062b4b24_153362_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/raspi-photoframe/8ffcb7bfb32b5079533396b7542ed9a1_hu8982ae701f5d02b9ab9d1e54062b4b24_153362_fa36f9d2badcc15fd6500bcdc35fea83.webp"
width="760"
height="504"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
Raspberry Pi Imager でOSを書き込む
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;p>32bit・64bitどちらでも問題なく動作します。&lt;/p>
&lt;h3 id="fbi-のインストール">fbi のインストール&lt;/h3>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">sudo apt-get -y install fbi
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h4 id="パーミッションの付与">パーミッションの付与&lt;/h4>
&lt;p>デフォルトではスーパーユーザー以外は fbi で画像を表示できません。&lt;code>pi&lt;/code> ユーザーを &lt;code>video&lt;/code> グループに追加します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">pi@raspi3-photo:~ $ ls -Fla /dev/fb0
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">crw-rw---- &lt;span class="m">1&lt;/span> root video 29, &lt;span class="m">0&lt;/span> Apr &lt;span class="m">7&lt;/span> 10:33 /dev/fb0
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">sudo usermod -aG video pi
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="rclone-のインストール">rclone のインストール&lt;/h3>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">curl https://rclone.org/install.sh &lt;span class="p">|&lt;/span> sudo bash
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>インストール後、&lt;code>rclone config&lt;/code> でGoogle Driveとの認証設定を行います。&lt;/p>
&lt;div class="alert alert-note">
&lt;div>
SSH接続のみのヘッドレス環境では、&lt;code>rclone config&lt;/code> 実行中にブラウザ認証用のURLが表示されます。そのURLをPC側のブラウザで開いてGoogleアカウントを認証してください。
&lt;/div>
&lt;/div>
&lt;h2 id="スライドショープログラムの実装">スライドショープログラムの実装&lt;/h2>
&lt;h3 id="アルゴリズム">アルゴリズム&lt;/h3>
&lt;p>以下の流れで動作します。&lt;/p>
&lt;ol>
&lt;li>&lt;code>rclone ls&lt;/code> でクラウドストレージ上の指定フォルダの画像一覧を取得&lt;/li>
&lt;li>一定数取得できた時点でランダムに画像のダウンロードを開始&lt;/li>
&lt;li>ダウンロードできた画像から順に &lt;code>fbi&lt;/code> で表示&lt;/li>
&lt;li>バックグラウンドで次の画像を取得し続ける&lt;/li>
&lt;li>指定時間が来たらランダムに次の画像へ切り替え&lt;/li>
&lt;li>重み付きランダム選択で、表示済み画像の優先度を下げ偏りを防ぐ&lt;/li>
&lt;li>週1回 &lt;code>rclone ls&lt;/code> でデータベースをマージして新着写真を反映&lt;/li>
&lt;li>データベースはファイルではなくメモリ上に保持（マージ速度改善）&lt;/li>
&lt;/ol>
&lt;h3 id="言語python">言語：Python&lt;/h3>
&lt;p>スライドショー制御スクリプトはPythonで実装しました。オブジェクト指向で設計し直した改良版では、起動から最初の画像表示までの時間を&lt;strong>旧バージョン比1700%高速化&lt;/strong>しています。&lt;/p>
&lt;p>Pythonの学習には &lt;a href="https://www.udemy.com/course/python-beginner/" target="_blank" rel="noopener">現役シリコンバレーエンジニアが教えるPython 3 入門 + 応用（Udemy）&lt;/a> が参考になりました。&lt;/p>
&lt;h2 id="ソースコード">ソースコード&lt;/h2>
&lt;p>作成したプログラムはGitHubで公開しています。&lt;/p>
&lt;p>&lt;a href="https://github.com/yukishita/photoView4" target="_blank" rel="noopener">GitHub - yukishita/photoView4：クラウド対応スライドショープログラム&lt;/a>&lt;/p>
&lt;h2 id="使い方">使い方&lt;/h2>
&lt;p>crontab に以下を追加して、起動時に自動実行します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">@reboot /home/pi/photoView4/photoView4.sh
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="デモンストレーション">デモンストレーション&lt;/h2>
&lt;p>改良版（v4）のデモ動画です。旧バージョンと比べて起動から表示までの時間が大幅に短縮されています。&lt;/p>
&lt;div style="position: relative; padding-bottom: 56.25%; height: 0; overflow: hidden;">
&lt;iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen="allowfullscreen" loading="eager" referrerpolicy="strict-origin-when-cross-origin" src="https://www.youtube.com/embed/VP7y_E34EJA?autoplay=0&amp;controls=1&amp;end=0&amp;loop=0&amp;mute=0&amp;start=0" style="position: absolute; top: 0; left: 0; width: 100%; height: 100%; border:0;" title="YouTube video"
>&lt;/iframe>
&lt;/div>
&lt;h3 id="旧バージョン参考">旧バージョン（参考）&lt;/h3>
&lt;p>ファイルリストをすべて取得してから動作するため起動が遅い版です。&lt;/p>
&lt;div style="position: relative; padding-bottom: 56.25%; height: 0; overflow: hidden;">
&lt;iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen="allowfullscreen" loading="eager" referrerpolicy="strict-origin-when-cross-origin" src="https://www.youtube.com/embed/-dxP_aHSjIU?autoplay=0&amp;controls=1&amp;end=0&amp;loop=0&amp;mute=0&amp;start=0" style="position: absolute; top: 0; left: 0; width: 100%; height: 100%; border:0;" title="YouTube video"
>&lt;/iframe>
&lt;/div>
&lt;h2 id="tips指定時刻にディスプレイの電源を切る">Tips：指定時刻にディスプレイの電源を切る&lt;/h2>
&lt;p>24時間表示し続けると電気代がかさむため、HDMI接続時は &lt;code>vcgencmd&lt;/code> で電源スケジュールを設定できます。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">&lt;span class="m">0&lt;/span> &lt;span class="m">0&lt;/span> * * * /usr/bin/vcgencmd display_power &lt;span class="m">0&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="m">30&lt;/span> &lt;span class="m">6&lt;/span> * * * /usr/bin/vcgencmd display_power &lt;span class="m">1&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>上記の例では午前0時にOFF・午前6時30分にONとなります。人感センサーや照度センサーと組み合わせてさらに自動化することも可能です。&lt;/p>
&lt;h2 id="まとめ">まとめ&lt;/h2>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>構成要素&lt;/th>
&lt;th>役割&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>Raspberry Pi 4&lt;/td>
&lt;td>メインコンピューター（低消費電力・常時稼働）&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>モバイルモニター&lt;/td>
&lt;td>FullHD・IPS・高視野角で写真を高品質表示&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>fbi&lt;/td>
&lt;td>CLIからフレームバッファに直接画像を表示&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>rclone&lt;/td>
&lt;td>Google Driveから写真を自動ダウンロード&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Python&lt;/td>
&lt;td>スライドショー制御・重み付きランダム選択&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;p>Raspberry Pi 4を使いましたが、Raspberry Pi Zero 2 Wでも同様の構成で動作可能です。常時通電する用途なので、消費電力の小さい機種を選ぶとランニングコストを抑えられます。&lt;/p></description></item><item><title>Raspberry Pi 3 + 公式7インチタッチスクリーンで照度センサー対応フォトフレームを自作する【BH1750FVI + I2C + Python】</title><link>https://yre.jp/post/raspi-photoframe-with-sensor/</link><pubDate>Tue, 19 Jul 2022 00:00:00 +0000</pubDate><guid>https://yre.jp/post/raspi-photoframe-with-sensor/</guid><description>&lt;p>以前 Raspberry Pi 4 でクラウド対応フォトフレームを作りましたが、今回は余っていた Raspberry Pi 3 と公式7インチタッチスクリーンで別バージョンを構築しました。さらに照度センサーを追加して、部屋の明るさに応じてディスプレイ輝度が自動調整される機能を実装しています。&lt;/p>
&lt;h2 id="用意するもの">用意するもの&lt;/h2>
&lt;h3 id="raspberry-pi-3">Raspberry Pi 3&lt;/h3>
&lt;a href="https://www.amazon.co.jp/dp/B082QN6L1N?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/71wjyr2fsJL._AC_SL1200_.jpg" alt="Raspberry Pi 3 Model B シングルボードコンピュータ">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">Raspberry Pi 3 Model B シングルボードコンピュータ&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="raspberry-pi-公式7インチタッチスクリーン">Raspberry Pi 公式7インチタッチスクリーン&lt;/h3>
&lt;p>800×480px・24ビットRGBカラー・60fps対応。最大10点のマルチタッチに対応しています。&lt;/p>
&lt;a href="https://www.amazon.co.jp/dp/B01LC7U4XW?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/6188oB1j-OL._AC_SL1024_.jpg" alt="Raspberry Pi 公式 7インチ タッチスクリーン LCD">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">Raspberry Pi 公式 7インチ タッチスクリーン LCD&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h3 id="公式タッチスクリーン用ケース">公式タッチスクリーン用ケース&lt;/h3>
&lt;p>Raspberry Pi 3 Model B と7インチディスプレイを一体で収納できるケースです。&lt;/p>
&lt;a href="https://www.amazon.co.jp/dp/B01N6786IE?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/41PUW&amp;#43;GgD0L._AC_.jpg" alt="Raspberry Pi &amp;amp; 7インチ LCDタッチスクリーン 拡張ボードケース ABS樹脂（黒）">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">Raspberry Pi &amp;amp; 7インチ LCDタッチスクリーン 拡張ボードケース ABS樹脂（黒）&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h2 id="ディスプレイの接続">ディスプレイの接続&lt;/h2>
&lt;p>&lt;a href="https://www.raspberrypi.com/documentation/accessories/display.html" target="_blank" rel="noopener">Raspberry Pi Touch Display 公式ドキュメント&lt;/a> を参考にリボンケーブルと電源を接続します。&lt;/p>
&lt;div class="alert alert-note">
&lt;div>
Raspberry Pi を背面ディスプレイに取り付ける場合、リボンケーブルの向きに注意してください。電源ケーブル（赤/黒）は、赤を5Vピン・黒をGNDピンに接続します。
&lt;/div>
&lt;/div>
&lt;h2 id="公式ディスプレイの画面回転設定">公式ディスプレイの画面回転設定&lt;/h2>
&lt;p>デフォルト状態では表示が180度回転しているため、設定ファイルで反転します。&lt;/p>
&lt;div class="alert alert-note">
&lt;div>
&lt;p>以下の &lt;code>lcd_rotate=2&lt;/code> は &lt;strong>Raspberry Pi OS Bullseye 以前（レガシー/FKMSモード）向け&lt;/strong>の設定です。Bookworm（2023年以降）では &lt;code>lcd_rotate&lt;/code> は公式には非推奨で、画面回転には「Screen Configuration」GUIツールの使用が案内されています。&lt;/p>
&lt;p>また、config.txt のパスも OS バージョンによって異なります。&lt;/p>
&lt;ul>
&lt;li>&lt;strong>Bullseye 以前&lt;/strong>：&lt;code>/boot/config.txt&lt;/code>&lt;/li>
&lt;li>&lt;strong>Bookworm 以降&lt;/strong>：&lt;code>/boot/firmware/config.txt&lt;/code>&lt;/li>
&lt;/ul>
&lt;/div>
&lt;/div>
&lt;p>&lt;strong>Bullseye 以前（レガシー/FKMSモード）の場合：&lt;/strong>&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">sudo vi /boot/config.txt
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>以下を追記します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="cl">lcd_rotate=2
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="スライドショー用プログラム">スライドショー用プログラム&lt;/h2>
&lt;p>スライドショー制御には、別記事で紹介している自作Pythonスクリプト（&lt;a href="https://github.com/yukishita/photoView4" target="_blank" rel="noopener">photoView4&lt;/a>）を流用しています。&lt;/p>
&lt;h2 id="ディスプレイの輝度調整">ディスプレイの輝度調整&lt;/h2>
&lt;p>フォトフレームとして常時表示していると、夜間など暗い環境では画面が眩しく感じます。公式7インチディスプレイは、以下のコマンドでバックライト輝度を変更できます。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">&lt;span class="nb">echo&lt;/span> &lt;span class="s2">&amp;#34;100&amp;#34;&lt;/span> &lt;span class="p">|&lt;/span> sudo tee /sys/class/backlight/rpi_backlight/brightness
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>&lt;code>/sys/class/backlight/rpi_backlight/brightness&lt;/code> に0〜255の値を書き込むことで輝度を制御できます。&lt;/p>
&lt;h2 id="照度センサーbh1750fviの追加">照度センサー（BH1750FVI）の追加&lt;/h2>
&lt;p>輝度を手動設定するだけでなく、部屋の明るさに応じて自動で輝度を変えたいと考え、照度センサーを追加しました。&lt;/p>
&lt;h3 id="使用パーツ">使用パーツ&lt;/h3>
&lt;a href="https://amzn.to/3PckLei" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/615BETFGkDL._AC_SY450_.jpg" alt="BH1750FVI 周囲光トランスデューサ I2C 出力 エレクトロニクス向けの連続および単一測定アプローチ 環境光観測コンポーネント">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">BH1750FVI 周囲光トランスデューサ I2C 出力 エレクトロニクス向けの連続および単一測定アプローチ 環境光観測コンポーネント&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;a href="https://www.amazon.co.jp/gp/product/B06Y48V9DL?tag=snowunderco07-22" target="_blank" rel="noopener nofollow sponsored" class="amazon-card">
&lt;div class="amazon-card-image">
&lt;img src="https://m.media-amazon.com/images/I/81yjq1pkiGL._SL1500_.jpg" alt="ELEGOO 120本 デュポンワイヤー ジャンパーワイヤー オス-メス/オス-オス/メス-メス セット">
&lt;/div>
&lt;div class="amazon-card-info">
&lt;div class="amazon-card-title">ELEGOO 120本 デュポンワイヤー ジャンパーワイヤー オス-メス/オス-オス/メス-メス セット&lt;/div>
&lt;div class="amazon-card-meta">
&lt;span class="amazon-btn">Amazonで見る&lt;/span>
&lt;/div>
&lt;/div>
&lt;/a>
&lt;h2 id="raspberry-pi-と-i2c-接続">Raspberry Pi と I2C 接続&lt;/h2>
&lt;p>BH1750FVI は I2C プロトコルで通信します。&lt;a href="https://www.raspberrypi.com/documentation/computers/os.html#gpio-and-the-40-pin-header" target="_blank" rel="noopener">Raspberry Pi GPIO ピン配置&lt;/a> を参照して接続します。&lt;/p>
&lt;p>
&lt;figure id="figure-raspberry-pi-gpioピン配置図出典raspberry-pi公式ドキュメント">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="Raspberry Piの40ピンGPIOヘッダーのピン配置図。SDA（GPIO2, Pin3）とSCL（GPIO3, Pin5）のI2Cピン位置を示している" srcset="
/media/raspi-photoframe-with-sensor/GPIO-Pinout-Diagram-2_hua49859c3abb8d59effc7f48992911ff2_206936_43d9d80c817fbd45d29cc36e3b5ca73e.webp 400w,
/media/raspi-photoframe-with-sensor/GPIO-Pinout-Diagram-2_hua49859c3abb8d59effc7f48992911ff2_206936_d6d457c064379b94134319d1e0002c6f.webp 760w,
/media/raspi-photoframe-with-sensor/GPIO-Pinout-Diagram-2_hua49859c3abb8d59effc7f48992911ff2_206936_1200x1200_fit_q75_h2_lanczos_3.webp 1200w"
src="https://yre.jp/media/raspi-photoframe-with-sensor/GPIO-Pinout-Diagram-2_hua49859c3abb8d59effc7f48992911ff2_206936_43d9d80c817fbd45d29cc36e3b5ca73e.webp"
width="760"
height="436"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
Raspberry Pi GPIOピン配置図（出典：Raspberry Pi公式ドキュメント）
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;h3 id="接続対応表">接続対応表&lt;/h3>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>Raspberry Pi&lt;/th>
&lt;th>GPIOピン番号&lt;/th>
&lt;th>BH1750FVI&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>GPIO2 (SDA)&lt;/td>
&lt;td>3&lt;/td>
&lt;td>SDA&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>GPIO3 (SCL)&lt;/td>
&lt;td>5&lt;/td>
&lt;td>SCL&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>5V Power&lt;/td>
&lt;td>2&lt;/td>
&lt;td>VCC&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Ground&lt;/td>
&lt;td>14&lt;/td>
&lt;td>ADO&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Ground&lt;/td>
&lt;td>20&lt;/td>
&lt;td>GND&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;p>
&lt;figure id="figure-bh1750fvi-をi2cで接続した配線の様子">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="GY-30 BH1750FVI照度センサーをRaspberry Pi 3にジャンパーワイヤーでI2C接続した実際の配線写真" srcset="
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1410_hu98206837892c374cd2028613e5b10c88_691631_c96c52f9123cb52726bbc85d7347db81.webp 400w,
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1410_hu98206837892c374cd2028613e5b10c88_691631_7b5ac30237dcef389547e52e6e3b9297.webp 760w,
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1410_hu98206837892c374cd2028613e5b10c88_691631_1200x1200_fit_q75_h2_lanczos.webp 1200w"
src="https://yre.jp/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1410_hu98206837892c374cd2028613e5b10c88_691631_c96c52f9123cb52726bbc85d7347db81.webp"
width="760"
height="507"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
BH1750FVI をI2Cで接続した配線の様子
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;h2 id="照度センサーの動作確認python">照度センサーの動作確認（Python）&lt;/h2>
&lt;p>接続後、Python で照度データを取得できるか確認します。&lt;a href="https://github.com/kujiraitakahiro/RaspberryPi/blob/master/bh1750fvi.py" target="_blank" rel="noopener">参考コード（GitHub）&lt;/a> を参考に実装しました。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-python" data-lang="python">&lt;span class="line">&lt;span class="cl">&lt;span class="ch">#!/usr/bin/python3&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kn">import&lt;/span> &lt;span class="nn">smbus&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="n">Bus&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="n">smbus&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">SMBus&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="mi">1&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="n">Addr&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="mh">0x23&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="n">LxRead&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="n">Bus&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">read_i2c_block_data&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="n">Addr&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="mh">0x11&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="nb">print&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s2">&amp;#34;照度: &amp;#34;&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="nb">str&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="n">LxRead&lt;/span>&lt;span class="p">[&lt;/span>&lt;span class="mi">1&lt;/span>&lt;span class="p">]&lt;/span> &lt;span class="o">*&lt;/span> &lt;span class="mi">10&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="s2">&amp;#34; ルクス&amp;#34;&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="n">LxRead2&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="n">Bus&lt;/span>&lt;span class="o">.&lt;/span>&lt;span class="n">read_i2c_block_data&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="n">Addr&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="mh">0x10&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="nb">print&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s2">&amp;#34;輝度: &amp;#34;&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="nb">str&lt;/span>&lt;span class="p">((&lt;/span>&lt;span class="n">LxRead2&lt;/span>&lt;span class="p">[&lt;/span>&lt;span class="mi">0&lt;/span>&lt;span class="p">]&lt;/span> &lt;span class="o">*&lt;/span> &lt;span class="mi">256&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="n">LxRead2&lt;/span>&lt;span class="p">[&lt;/span>&lt;span class="mi">1&lt;/span>&lt;span class="p">])&lt;/span> &lt;span class="o">/&lt;/span> &lt;span class="mf">1.2&lt;/span>&lt;span class="p">))&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>実行すると照度が取得できます。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-text" data-lang="text">&lt;span class="line">&lt;span class="cl">root@raspi3-photo:~# python br.py
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">照度: 1650 ルクス
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">輝度: 990.8333333333334
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="輝度自動調整プログラムの実装">輝度自動調整プログラムの実装&lt;/h2>
&lt;p>取得した照度に応じてバックライト輝度を滑らかに変化させるため、10ms周期で動作するPythonプログラムを作成しました。&lt;/p>
&lt;p>仕組みは以下のとおりです：&lt;/p>
&lt;ul>
&lt;li>照度レベルごとにターゲット輝度を定義&lt;/li>
&lt;li>取得した照度に応じてディスプレイ輝度を1ステップずつインクリメント/デクリメント&lt;/li>
&lt;li>SMBus（I2C）通信は取得間隔を300ms以上空けないと正常な値が取れないため、300ms周期でポーリング&lt;/li>
&lt;/ul>
&lt;h2 id="照度センサーの設置">照度センサーの設置&lt;/h2>
&lt;p>センサーは前面から光が当たる背面の出っぱった部分に設置しました。&lt;/p>
&lt;p>
&lt;figure id="figure-照度センサーをケース背面に設置した様子">
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img alt="GY-30 BH1750FVI照度センサーをRaspberry Pi 3公式タッチスクリーンケースの背面出っぱりに設置した実際の写真" srcset="
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1407_hu98206837892c374cd2028613e5b10c88_594389_c8e1166602273b79f64bef721cf2db83.webp 400w,
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1407_hu98206837892c374cd2028613e5b10c88_594389_62c0ff78d1802062e2b677dae092cc5d.webp 760w,
/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1407_hu98206837892c374cd2028613e5b10c88_594389_1200x1200_fit_q75_h2_lanczos.webp 1200w"
src="https://yre.jp/media/raspi-photoframe-with-sensor/ILCE-7M4-_DSC1407_hu98206837892c374cd2028613e5b10c88_594389_c8e1166602273b79f64bef721cf2db83.webp"
width="760"
height="507"
loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;figcaption>
照度センサーをケース背面に設置した様子
&lt;/figcaption>&lt;/figure>
&lt;/p>
&lt;h2 id="ソースコード">ソースコード&lt;/h2>
&lt;p>作成したプログラムはGitHubで公開しています。&lt;/p>
&lt;p>&lt;a href="https://github.com/yukishita/lcdBrightness2" target="_blank" rel="noopener">GitHub - yukishita/lcdBrightness2：BH1750FVI 照度センサーで Raspberry Pi 公式ディスプレイ輝度を自動調整するプログラム&lt;/a>&lt;/p>
&lt;h2 id="デモ動画">デモ動画&lt;/h2>
&lt;p>照度に応じてディスプレイ輝度が滑らかに変化する様子です。&lt;/p>
&lt;div style="position: relative; padding-bottom: 56.25%; height: 0; overflow: hidden;">
&lt;iframe allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen="allowfullscreen" loading="eager" referrerpolicy="strict-origin-when-cross-origin" src="https://www.youtube.com/embed/R6XGl3KGRYA?autoplay=0&amp;controls=1&amp;end=0&amp;loop=0&amp;mute=0&amp;start=0" style="position: absolute; top: 0; left: 0; width: 100%; height: 100%; border:0;" title="YouTube video"
>&lt;/iframe>
&lt;/div>
&lt;h2 id="まとめ">まとめ&lt;/h2>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>構成要素&lt;/th>
&lt;th>役割&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>Raspberry Pi 3&lt;/td>
&lt;td>メインコンピューター&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>公式7インチタッチスクリーン&lt;/td>
&lt;td>フォトフレーム表示（800×480px）&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>GY-30 BH1750FVI&lt;/td>
&lt;td>I2C接続の照度センサー&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>Python（smbus）&lt;/td>
&lt;td>I2C通信・輝度自動調整制御&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;p>照度センサーを追加することで、昼は明るく・夜は暗くと自動で輝度が変わり、実用的なフォトフレームになりました。Raspberry Pi Zero 2 W でも同様の構成で動作すると思われます。&lt;/p></description></item><item><title>【Mac】DjangoをHomebrewでインストールしてローカルサーバーを起動する方法【初心者向け】</title><link>https://yre.jp/post/jango_mac/</link><pubDate>Fri, 15 Apr 2022 00:00:00 +0000</pubDate><guid>https://yre.jp/post/jango_mac/</guid><description>&lt;p>MacにDjangoをインストールしてローカルサーバーを起動するまでの手順を初心者向けにまとめます。Homebrewを使ったPythonの導入から、仮想環境の作成、Djangoプロジェクトの起動まで順を追って解説します。&lt;/p>
&lt;h2 id="検証環境">検証環境&lt;/h2>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>項目&lt;/th>
&lt;th>バージョン&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>端末&lt;/td>
&lt;td>MacBook Pro (Apple Silicon)&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>OS&lt;/td>
&lt;td>macOS Monterey 12.3.1&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;h2 id="django-とは">Django とは？&lt;/h2>
&lt;p>&lt;a href="https://www.djangoproject.com/" target="_blank" rel="noopener">Django&lt;/a> は Python で書かれたオープンソースの Web フレームワークです。管理画面・認証・ORM（データベース操作）などの機能があらかじめ揃っており、Webアプリケーションを効率よく開発できます。Instagram や Disqus など大規模サービスでの採用実績もあります。&lt;/p>
&lt;p>この記事では、まず Django を起動するところを目標にします。&lt;/p>
&lt;h2 id="ステップ1homebrew-のインストール">ステップ1：Homebrew のインストール&lt;/h2>
&lt;p>Djangoは Python で動くため、まず Python を用意します。Mac への Python 導入方法はいくつかありますが、パッケージ管理が楽な &lt;a href="https://brew.sh/ja/" target="_blank" rel="noopener">Homebrew&lt;/a> を使う方法がおすすめです。&lt;/p>
&lt;p>ターミナルに以下のコマンドを貼り付けて実行します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">/bin/bash -c &lt;span class="s2">&amp;#34;&lt;/span>&lt;span class="k">$(&lt;/span>curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh&lt;span class="k">)&lt;/span>&lt;span class="s2">&amp;#34;&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>管理者パスワードを入力するとインストールが始まります。&lt;code>Installation successful!&lt;/code> が表示されれば完了です。&lt;/p>
&lt;h2 id="ステップ2python-のインストール">ステップ2：Python のインストール&lt;/h2>
&lt;p>Homebrew がインストールできたら Python をインストールします。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">brew install python3
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>インストール後、バージョンを確認します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">python3 --version
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1"># Python 3.x.x と表示されればOK&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="ステップ3python-のパスを通す">ステップ3：Python のパスを通す&lt;/h2>
&lt;p>Homebrew でインストールした Python は &lt;code>/opt/homebrew/bin/&lt;/code> 以下に置かれます。システムのデフォルト Python（&lt;code>/usr/bin/python3&lt;/code>）より優先して使われるよう、パスを設定します。&lt;/p>
&lt;p>現在のパスを確認します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">which python3
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1"># /usr/bin/python3 と表示される場合は設定が必要&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>&lt;code>~/.zprofile&lt;/code> にパスを追記します（macOS Monterey 以降、zsh ではこのファイルがログイン時に自動読み込みされます）。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">&lt;span class="nb">echo&lt;/span> &lt;span class="s1">&amp;#39;export PATH=/opt/homebrew/bin/:$PATH&amp;#39;&lt;/span> &amp;gt;&amp;gt; ~/.zprofile
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>ターミナルを再起動後、確認します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">which python3
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1"># /opt/homebrew/bin/python3 と表示されればOK&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="ステップ4django-のインストール">ステップ4：Django のインストール&lt;/h2>
&lt;h3 id="作業フォルダの作成">作業フォルダの作成&lt;/h3>
&lt;p>任意の作業ディレクトリを作成して移動します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">mkdir myproject &lt;span class="o">&amp;amp;&amp;amp;&lt;/span> &lt;span class="nb">cd&lt;/span> myproject
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="python-仮想環境のセットアップ">Python 仮想環境のセットアップ&lt;/h3>
&lt;p>Python の &lt;strong>仮想環境（venv）&lt;/strong> とは、プロジェクトごとに独立したパッケージ環境を作る仕組みです。異なるプロジェクトで異なるバージョンのライブラリを使い分けられるため、開発では必ず利用することが推奨されています。&lt;/p>
&lt;p>&lt;code>django&lt;/code> という名前の仮想環境を作成し、有効化します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">python3 -m venv django
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="nb">source&lt;/span> ./django/bin/activate
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1"># (django) がプロンプトの先頭に表示されれば有効化成功&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="pip-で-django-をインストール">pip で Django をインストール&lt;/h3>
&lt;p>仮想環境が有効な状態で Django をインストールします。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">pip3 install django
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>&lt;code>Successfully installed django-x.x.x&lt;/code> と表示されればインストール完了です。&lt;/p>
&lt;h2 id="ステップ5django-プロジェクトの作成と起動">ステップ5：Django プロジェクトの作成と起動&lt;/h2>
&lt;h3 id="プロジェクトの作成">プロジェクトの作成&lt;/h3>
&lt;p>&lt;code>django-admin startproject &amp;lt;プロジェクト名&amp;gt;&lt;/code> でプロジェクトの雛形を生成します。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">django-admin startproject firstproject
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="nb">cd&lt;/span> firstproject
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h3 id="ローカルサーバーの起動">ローカルサーバーの起動&lt;/h3>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">python3 manage.py runserver
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>起動に成功すると以下のように表示されます。&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">Watching &lt;span class="k">for&lt;/span> file changes with StatReloader
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Performing system checks...
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">System check identified no issues &lt;span class="o">(&lt;/span>&lt;span class="m">0&lt;/span> silenced&lt;span class="o">)&lt;/span>.
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">You have &lt;span class="m">18&lt;/span> unapplied migration&lt;span class="o">(&lt;/span>s&lt;span class="o">)&lt;/span>. Your project may not work properly &lt;span class="k">until&lt;/span> you apply the migrations &lt;span class="k">for&lt;/span> app&lt;span class="o">(&lt;/span>s&lt;span class="o">)&lt;/span>: admin, auth, contenttypes, sessions.
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Run &lt;span class="s1">&amp;#39;python manage.py migrate&amp;#39;&lt;/span> to apply them.
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Django version 4.0.4, using settings &lt;span class="s1">&amp;#39;firstproject.settings&amp;#39;&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Starting development server at http://127.0.0.1:8000/
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">Quit the server with CONTROL-C.
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;div class="alert alert-note">
&lt;div>
&lt;code>unapplied migration(s)&lt;/code> という警告が表示されますが、これはDjangoの内部データベース（管理画面・認証機能用）がまだ初期化されていないためです。動作確認だけなら無視して問題ありません。後で &lt;code>python3 manage.py migrate&lt;/code> を実行すると解消できます。
&lt;/div>
&lt;/div>
&lt;p>ブラウザで &lt;code>http://127.0.0.1:8000/&lt;/code> を開き、Djangoのウェルカムページが表示されれば成功です。&lt;/p>
&lt;h2 id="まとめ">まとめ&lt;/h2>
&lt;p>MacへのDjangoインストール手順をまとめます。&lt;/p>
&lt;ol>
&lt;li>Homebrew をインストール&lt;/li>
&lt;li>&lt;code>brew install python3&lt;/code> で Python を導入&lt;/li>
&lt;li>&lt;code>~/.zprofile&lt;/code> でパスを設定&lt;/li>
&lt;li>&lt;code>python3 -m venv&lt;/code> で仮想環境を作成・有効化&lt;/li>
&lt;li>&lt;code>pip3 install django&lt;/code> でインストール&lt;/li>
&lt;li>&lt;code>django-admin startproject&lt;/code> でプロジェクト作成&lt;/li>
&lt;li>&lt;code>python3 manage.py runserver&lt;/code> でサーバー起動&lt;/li>
&lt;/ol>
&lt;p>次のステップとして、&lt;a href="https://docs.djangoproject.com/ja/stable/intro/tutorial01/" target="_blank" rel="noopener">Django公式チュートリアル&lt;/a>を進めると、ビュー・モデル・テンプレートの基本が体系的に学べます。&lt;/p></description></item></channel></rss>