POSA_LEAKSMS/raspberry_pi4_sht30/WIRING.html
cw2007 2046b2f292 docs(wiring): 누수 저항식 2선 프로브·SHT30 모듈 직결로 배선도 정정
- 누수 §4 배선도: 3핀(VCC/SIG/GND) → 2전극 프로브(전극 A→3V3, 전극 B→GPIO17).
  10MΩ 풀다운은 GPIO17↔GND 보드 부품(센서 선 아님)으로 명시. 펌웨어(ACTIVE_LOW=False) 일치.
  §2 범례·§3 핀표·§8 통합표 GND 문구도 "풀다운용(센서 선 아님)"으로 통일.
- SHT30 §4: 외부 풀업 R1/R2·SDA hop 제거 → VCC/GND/SDA/SCL 4선 직결(내장 풀업). §3 표 문구 갱신.
- 납품 리포트(센서 형태·내용): 누수 "2선 저항식 프로브", SHT30 "모듈 직결" 반영.
- 브라우저 렌더 검증: 두 §4 텍스트·선 겹침 0.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_015Dj4n17ZvGAhga6D4pNRjn
2026-07-19 23:34:27 +09:00

545 lines
28 KiB
HTML
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Temp/Humidity Node Wiring & Pinmap — Pi-B / SHT30 (sensor_id=2)</title>
<style>
:root{
--ink:#1a1d21; --muted:#5c6570; --line:#dfe3e8; --bg:#eef1f4; --card:#ffffff;
--accent:#1971c2; --accent-d:#155a9c; --warn:#e03131; --warnbg:#fff5f5;
--ok:#2f9e44; --gnd:#343a40; --chip:#eef2f6; --code:#0b3d2e;
--mono:"D2Coding","Consolas","Menlo","Courier New",ui-monospace,monospace;
--sans:"Malgun Gothic","Apple SD Gothic Neo","Noto Sans KR","Segoe UI",system-ui,-apple-system,sans-serif;
}
*{box-sizing:border-box;}
html,body{margin:0;padding:0;}
body{
font-family:var(--sans); color:var(--ink); background:var(--bg);
line-height:1.6; -webkit-font-smoothing:antialiased;
}
.wrap{max-width:1000px; margin:0 auto; padding:22px 18px 60px;}
/* ---------- Header ---------- */
.hero{
background:linear-gradient(135deg,#1f2933 0%,#283746 55%,#2f4a5a 100%);
color:#fff; border-radius:16px; padding:26px 28px;
box-shadow:0 8px 24px rgba(20,30,40,.18);
}
.hero .eyebrow{font-size:12.5px; letter-spacing:.14em; text-transform:uppercase;
color:#9fc3e0; font-weight:700; margin:0 0 6px;}
.hero h1{margin:0 0 8px; font-size:27px; line-height:1.25; font-weight:800;}
.hero p.sum{margin:0 0 16px; font-size:14.5px; color:#d7e2ec; max-width:72ch;}
.chips{display:flex; flex-wrap:wrap; gap:8px;}
.chip{
display:inline-flex; align-items:center; gap:6px;
background:rgba(255,255,255,.12); border:1px solid rgba(255,255,255,.22);
color:#eef5fb; font-size:12.5px; font-weight:600; padding:5px 11px; border-radius:999px;
}
.chip.mono{font-family:var(--mono); letter-spacing:.01em;}
.chip b{color:#fff;}
/* ---------- Sections ---------- */
section{
background:var(--card); border:1px solid var(--line); border-radius:14px;
padding:22px 24px; margin-top:20px; box-shadow:0 2px 10px rgba(20,30,40,.05);
}
h2{
display:flex; align-items:center; gap:11px; margin:0 0 16px;
font-size:19px; font-weight:800; color:var(--ink);
}
h2 .n{
flex:0 0 auto; width:30px; height:30px; border-radius:9px;
background:var(--accent); color:#fff; font-size:15px; font-weight:800;
display:flex; align-items:center; justify-content:center;
}
h2 small{font-weight:600; font-size:13px; color:var(--muted);}
/* ---------- Pinmap SVG ---------- */
.svg-pin{display:block; width:100%; max-width:460px; height:auto; margin:2px auto 0;}
.diagram-cap{text-align:center; color:var(--muted); font-size:12.5px; margin:12px 0 0;}
.legend{
display:flex; flex-wrap:wrap; justify-content:center; gap:12px 18px;
margin:16px auto 2px; max-width:640px;
}
.legend span{display:inline-flex; align-items:center; gap:7px; font-size:12.5px; color:var(--ink);}
.sw{width:15px; height:15px; border-radius:50%; flex:0 0 auto; border:1px solid rgba(0,0,0,.15);}
.sw.pwr{background:#2f9e44;} .sw.i2c{background:#1971c2;}
.sw.gnd{background:#343a40;}
.sw.altgnd{background:#ced4da; border:1.5px dashed #868e96;}
.sw.off{background:#dee2e6;}
/* SVG element classes */
.p-pwr{fill:#2f9e44; stroke:#248a3b; stroke-width:1.5;}
.p-i2c{fill:#1971c2; stroke:#155a9c; stroke-width:1.5;}
.p-gnd{fill:#343a40; stroke:#1f2429; stroke-width:1.5;}
.p-altgnd{fill:#ced4da; stroke:#868e96; stroke-width:1.5; stroke-dasharray:3 2;}
.p-off{fill:#dee2e6; stroke:#c3c9cf; stroke-width:1;}
.rail{fill:#f1f3f5; stroke:#ced4da; stroke-width:1.5;}
.pnum{font-family:var(--mono); font-size:12px; font-weight:700; text-anchor:middle; dominant-baseline:central;}
.pnum-l{fill:#ffffff;} .pnum-d{fill:#495057;}
.plbl{font-family:var(--mono); font-size:12px; dominant-baseline:central;}
.lbl-l{text-anchor:end;} .lbl-r{text-anchor:start;}
.lbl-used{fill:#1a1d21; font-weight:700;}
.lbl-alt{fill:#5c6570; font-weight:600;}
.lbl-off{fill:#adb5bd; font-weight:500;}
.cap-svg{font-family:var(--sans); font-size:12.5px; fill:#5c6570; font-weight:600; text-anchor:middle;}
/* ---------- Table ---------- */
table{width:100%; border-collapse:collapse; font-size:14px;}
thead th{
background:#f1f4f7; color:#2b3541; text-align:left; font-weight:700;
padding:10px 12px; border-bottom:2px solid #ccd4dc; font-size:13px;
}
tbody td{padding:11px 12px; border-bottom:1px solid var(--line); vertical-align:top;}
tbody tr:last-child td{border-bottom:none;}
.mono{font-family:var(--mono);}
.pinbadge{
display:inline-block; min-width:26px; text-align:center; font-family:var(--mono);
font-weight:700; font-size:13px; color:#fff; background:var(--accent);
border-radius:6px; padding:2px 7px;
}
.pinbadge.gnd{background:var(--gnd);} .pinbadge.pwr{background:var(--ok);}
.pinbadge.na{background:#adb5bd;}
td .warn-inline{color:var(--warn); font-weight:700;}
/* ---------- Schematic ---------- */
.svg-sch{display:block; width:100%; max-width:840px; height:auto; margin:0 auto;}
.box{fill:#f8f9fa; stroke:#495057; stroke-width:2; rx:8;}
.boxtitle{font-family:var(--sans); font-size:14px; font-weight:800; fill:#1a1d21; text-anchor:middle;}
.term{font-family:var(--mono); font-size:12.5px; font-weight:700; fill:#2b3541;}
.w-pwr{stroke:#e03131; stroke-width:3; fill:none; stroke-linecap:round; stroke-linejoin:round;}
.w-i2c{stroke:#1971c2; stroke-width:3; fill:none; stroke-linecap:round; stroke-linejoin:round;}
.w-gnd{stroke:#343a40; stroke-width:3; fill:none; stroke-linecap:round; stroke-linejoin:round;}
.w-addr{stroke:#495057; stroke-width:2.5; fill:none; stroke-dasharray:6 4; stroke-linecap:round;}
.res{fill:#ffffff; stroke:#212529; stroke-width:2;}
.wlbl{font-family:var(--sans); font-size:12px; font-weight:700; fill:#2b3541;}
.rlbl{font-family:var(--mono); font-size:12px; font-weight:700; fill:#b02a2a;}
.jn{fill:#212529;}
.sch-note{color:var(--muted); font-size:12.5px; text-align:center; margin:12px 0 0;}
/* ---------- Callouts ---------- */
.warn{
background:var(--warnbg); border:1.5px solid #ffc9c9; border-left:6px solid var(--warn);
border-radius:12px; padding:16px 18px; margin:0 0 16px; display:flex; gap:14px; align-items:flex-start;
}
.warn .ic{flex:0 0 auto; width:34px; height:34px;}
.warn h3{margin:0 0 4px; color:#c92a2a; font-size:16px; font-weight:800;}
.warn p{margin:0; font-size:14px; color:#5a2020;}
.warn b{color:#c92a2a;}
ul.notes{margin:6px 0 0; padding:0; list-style:none;}
ul.notes li{position:relative; padding:7px 0 7px 24px; border-bottom:1px dashed var(--line); font-size:14px;}
ul.notes li:last-child{border-bottom:none;}
ul.notes li::before{content:""; position:absolute; left:4px; top:14px; width:8px; height:8px;
background:var(--accent); border-radius:2px; transform:rotate(45deg);}
code, .kbd{font-family:var(--mono); background:#eef2f6; color:#0b3d2e; padding:1px 6px; border-radius:5px; font-size:13px;}
.cmd{
font-family:var(--mono); background:#12211b; color:#c8f7d8; border-radius:10px;
padding:12px 14px; font-size:13.5px; margin:12px 0 0; overflow-x:auto;
}
.cmd .cm{color:#7fd6a3;} .cmd .ok{color:#ffd43b;}
/* ---------- Checklist ---------- */
ol.check{margin:0; padding:0; list-style:none; counter-reset:ck;}
ol.check li{
counter-increment:ck; position:relative; display:flex; align-items:flex-start; gap:12px;
padding:11px 4px 11px 0; border-bottom:1px solid var(--line); font-size:14px;
}
ol.check li:last-child{border-bottom:none;}
ol.check li .num{
flex:0 0 auto; width:24px; height:24px; border-radius:50%; background:#e7eef5; color:#1f5f97;
font-weight:800; font-size:12.5px; display:flex; align-items:center; justify-content:center;
}
ol.check li .num::before{content:counter(ck);}
ol.check li .cbox{flex:0 0 auto; width:18px; height:18px; border:2px solid #9aa6b1; border-radius:4px; margin-top:1px;}
ol.check li .txt{flex:1;}
ol.check li .txt b{color:var(--warn);}
footer{margin-top:26px; text-align:center; color:var(--muted); font-size:12px;}
/* ---------- Print ---------- */
@media print{
body{background:#fff;}
.wrap{max-width:none; padding:0;}
.hero{background:#fff !important; color:#111; border:2px solid #111; box-shadow:none;}
.hero .eyebrow{color:#444;} .hero p.sum{color:#222;}
.chip{background:#f2f2f2; color:#111; border:1px solid #999;}
.chip b{color:#000;}
h2 .n{background:#111;}
section{box-shadow:none; border:1px solid #999; break-inside:avoid; page-break-inside:avoid;}
table, tr, td, th, .warn, .card{break-inside:avoid; page-break-inside:avoid;}
.svg-pin, .svg-sch{max-width:100%;}
.cmd{background:#f2f2f2; color:#111; border:1px solid #999;}
a{color:#000;}
}
@media (max-width:560px){
.hero h1{font-size:22px;} h2{font-size:17px;}
}
</style>
</head>
<body>
<div class="wrap">
<!-- ============ 1. HEADER ============ -->
<header class="hero">
<p class="eyebrow">Field Installation Doc · Wiring &amp; Pinmap</p>
<h1>Temp/Humidity Node — Site 1 / Server Room</h1>
<p class="sum">
A measurement node connecting the SHT30 temperature/humidity sensor to the Raspberry Pi (Pi-B) over I2C (bus 1, address 0x44).
This node only reports readings to the server every <b>5 minutes</b>; high/low temperature and high/low humidity threshold decisions and SMS dispatch are handled by the server.
</p>
<div class="chips">
<span class="chip">Raspberry Pi 4 Model B</span>
<span class="chip mono">BCM2711</span>
<span class="chip">Raspberry Pi OS Bookworm 64-bit</span>
<span class="chip">Sensirion SHT30 (Hanjin Data P4422-3)</span>
<span class="chip mono">I2C bus <b>1</b></span>
<span class="chip mono">addr <b>0x44</b></span>
<span class="chip mono">sensor_id=<b>2</b></span>
<span class="chip">Report interval 5 min</span>
</div>
</header>
<!-- ============ 2. PINMAP SVG ============ -->
<section>
<h2><span class="n">2</span>40-Pin Header Pinmap Diagram <small>Used pins highlighted · others in gray</small></h2>
<svg class="svg-pin" viewBox="0 0 520 672" role="img" aria-label="Raspberry Pi 40-pin GPIO header pinmap">
<!-- caption -->
<text class="cap-svg" x="260" y="20">40-pin GPIO header (J8) · physical pin numbers</text>
<!-- rails -->
<rect class="rail" x="186" y="46" width="28" height="600" rx="14"/>
<rect class="rail" x="306" y="46" width="28" height="600" rx="14"/>
<!-- Row 1 : pin1 (square = pin1 marker) / pin2 -->
<rect class="p-pwr" x="188" y="48" width="24" height="24" rx="5"/>
<text class="pnum pnum-l" x="200" y="60">1</text>
<text class="plbl lbl-l lbl-used" x="176" y="60">3V3</text>
<circle class="p-off" cx="320" cy="60" r="12"/>
<text class="pnum pnum-d" x="320" y="60">2</text>
<text class="plbl lbl-r lbl-off" x="344" y="60">5V</text>
<!-- Row 2 : pin3 / pin4 -->
<circle class="p-i2c" cx="200" cy="90" r="12"/>
<text class="pnum pnum-l" x="200" y="90">3</text>
<text class="plbl lbl-l lbl-used" x="176" y="90">GPIO2 (SDA1)</text>
<circle class="p-off" cx="320" cy="90" r="12"/>
<text class="pnum pnum-d" x="320" y="90">4</text>
<text class="plbl lbl-r lbl-off" x="344" y="90">5V</text>
<!-- Row 3 : pin5 / pin6 -->
<circle class="p-i2c" cx="200" cy="120" r="12"/>
<text class="pnum pnum-l" x="200" y="120">5</text>
<text class="plbl lbl-l lbl-used" x="176" y="120">GPIO3 (SCL1)</text>
<circle class="p-gnd" cx="320" cy="120" r="12"/>
<text class="pnum pnum-l" x="320" y="120">6</text>
<text class="plbl lbl-r lbl-used" x="344" y="120">GND</text>
<!-- Row 4 : pin7 / pin8 -->
<circle class="p-off" cx="200" cy="150" r="12"/>
<text class="pnum pnum-d" x="200" y="150">7</text>
<text class="plbl lbl-l lbl-off" x="176" y="150">GPIO4</text>
<circle class="p-off" cx="320" cy="150" r="12"/>
<text class="pnum pnum-d" x="320" y="150">8</text>
<text class="plbl lbl-r lbl-off" x="344" y="150">GPIO14 (TXD)</text>
<!-- Row 5 : pin9 / pin10 -->
<circle class="p-altgnd" cx="200" cy="180" r="12"/>
<text class="pnum pnum-d" x="200" y="180">9</text>
<text class="plbl lbl-l lbl-alt" x="176" y="180">GND</text>
<circle class="p-off" cx="320" cy="180" r="12"/>
<text class="pnum pnum-d" x="320" y="180">10</text>
<text class="plbl lbl-r lbl-off" x="344" y="180">GPIO15 (RXD)</text>
<!-- Row 6 : pin11 / pin12 -->
<circle class="p-off" cx="200" cy="210" r="12"/>
<text class="pnum pnum-d" x="200" y="210">11</text>
<text class="plbl lbl-l lbl-off" x="176" y="210">GPIO17</text>
<circle class="p-off" cx="320" cy="210" r="12"/>
<text class="pnum pnum-d" x="320" y="210">12</text>
<text class="plbl lbl-r lbl-off" x="344" y="210">GPIO18</text>
<!-- Row 7 : pin13 / pin14 -->
<circle class="p-off" cx="200" cy="240" r="12"/>
<text class="pnum pnum-d" x="200" y="240">13</text>
<text class="plbl lbl-l lbl-off" x="176" y="240">GPIO27</text>
<circle class="p-altgnd" cx="320" cy="240" r="12"/>
<text class="pnum pnum-d" x="320" y="240">14</text>
<text class="plbl lbl-r lbl-alt" x="344" y="240">GND</text>
<!-- Row 8 : pin15 / pin16 -->
<circle class="p-off" cx="200" cy="270" r="12"/>
<text class="pnum pnum-d" x="200" y="270">15</text>
<text class="plbl lbl-l lbl-off" x="176" y="270">GPIO22</text>
<circle class="p-off" cx="320" cy="270" r="12"/>
<text class="pnum pnum-d" x="320" y="270">16</text>
<text class="plbl lbl-r lbl-off" x="344" y="270">GPIO23</text>
<!-- Row 9 : pin17 / pin18 -->
<circle class="p-off" cx="200" cy="300" r="12"/>
<text class="pnum pnum-d" x="200" y="300">17</text>
<text class="plbl lbl-l lbl-off" x="176" y="300">3V3</text>
<circle class="p-off" cx="320" cy="300" r="12"/>
<text class="pnum pnum-d" x="320" y="300">18</text>
<text class="plbl lbl-r lbl-off" x="344" y="300">GPIO24</text>
<!-- Row 10 : pin19 / pin20 -->
<circle class="p-off" cx="200" cy="330" r="12"/>
<text class="pnum pnum-d" x="200" y="330">19</text>
<text class="plbl lbl-l lbl-off" x="176" y="330">GPIO10 (MOSI)</text>
<circle class="p-altgnd" cx="320" cy="330" r="12"/>
<text class="pnum pnum-d" x="320" y="330">20</text>
<text class="plbl lbl-r lbl-alt" x="344" y="330">GND</text>
<!-- Row 11 : pin21 / pin22 -->
<circle class="p-off" cx="200" cy="360" r="12"/>
<text class="pnum pnum-d" x="200" y="360">21</text>
<text class="plbl lbl-l lbl-off" x="176" y="360">GPIO9 (MISO)</text>
<circle class="p-off" cx="320" cy="360" r="12"/>
<text class="pnum pnum-d" x="320" y="360">22</text>
<text class="plbl lbl-r lbl-off" x="344" y="360">GPIO25</text>
<!-- Row 12 : pin23 / pin24 -->
<circle class="p-off" cx="200" cy="390" r="12"/>
<text class="pnum pnum-d" x="200" y="390">23</text>
<text class="plbl lbl-l lbl-off" x="176" y="390">GPIO11 (SCLK)</text>
<circle class="p-off" cx="320" cy="390" r="12"/>
<text class="pnum pnum-d" x="320" y="390">24</text>
<text class="plbl lbl-r lbl-off" x="344" y="390">GPIO8 (CE0)</text>
<!-- Row 13 : pin25 / pin26 -->
<circle class="p-altgnd" cx="200" cy="420" r="12"/>
<text class="pnum pnum-d" x="200" y="420">25</text>
<text class="plbl lbl-l lbl-alt" x="176" y="420">GND</text>
<circle class="p-off" cx="320" cy="420" r="12"/>
<text class="pnum pnum-d" x="320" y="420">26</text>
<text class="plbl lbl-r lbl-off" x="344" y="420">GPIO7 (CE1)</text>
<!-- Row 14 : pin27 / pin28 -->
<circle class="p-off" cx="200" cy="450" r="12"/>
<text class="pnum pnum-d" x="200" y="450">27</text>
<text class="plbl lbl-l lbl-off" x="176" y="450">GPIO0 (ID_SD)</text>
<circle class="p-off" cx="320" cy="450" r="12"/>
<text class="pnum pnum-d" x="320" y="450">28</text>
<text class="plbl lbl-r lbl-off" x="344" y="450">GPIO1 (ID_SC)</text>
<!-- Row 15 : pin29 / pin30 -->
<circle class="p-off" cx="200" cy="480" r="12"/>
<text class="pnum pnum-d" x="200" y="480">29</text>
<text class="plbl lbl-l lbl-off" x="176" y="480">GPIO5</text>
<circle class="p-altgnd" cx="320" cy="480" r="12"/>
<text class="pnum pnum-d" x="320" y="480">30</text>
<text class="plbl lbl-r lbl-alt" x="344" y="480">GND</text>
<!-- Row 16 : pin31 / pin32 -->
<circle class="p-off" cx="200" cy="510" r="12"/>
<text class="pnum pnum-d" x="200" y="510">31</text>
<text class="plbl lbl-l lbl-off" x="176" y="510">GPIO6</text>
<circle class="p-off" cx="320" cy="510" r="12"/>
<text class="pnum pnum-d" x="320" y="510">32</text>
<text class="plbl lbl-r lbl-off" x="344" y="510">GPIO12</text>
<!-- Row 17 : pin33 / pin34 -->
<circle class="p-off" cx="200" cy="540" r="12"/>
<text class="pnum pnum-d" x="200" y="540">33</text>
<text class="plbl lbl-l lbl-off" x="176" y="540">GPIO13</text>
<circle class="p-altgnd" cx="320" cy="540" r="12"/>
<text class="pnum pnum-d" x="320" y="540">34</text>
<text class="plbl lbl-r lbl-alt" x="344" y="540">GND</text>
<!-- Row 18 : pin35 / pin36 -->
<circle class="p-off" cx="200" cy="570" r="12"/>
<text class="pnum pnum-d" x="200" y="570">35</text>
<text class="plbl lbl-l lbl-off" x="176" y="570">GPIO19</text>
<circle class="p-off" cx="320" cy="570" r="12"/>
<text class="pnum pnum-d" x="320" y="570">36</text>
<text class="plbl lbl-r lbl-off" x="344" y="570">GPIO16</text>
<!-- Row 19 : pin37 / pin38 -->
<circle class="p-off" cx="200" cy="600" r="12"/>
<text class="pnum pnum-d" x="200" y="600">37</text>
<text class="plbl lbl-l lbl-off" x="176" y="600">GPIO26</text>
<circle class="p-off" cx="320" cy="600" r="12"/>
<text class="pnum pnum-d" x="320" y="600">38</text>
<text class="plbl lbl-r lbl-off" x="344" y="600">GPIO20</text>
<!-- Row 20 : pin39 / pin40 -->
<circle class="p-altgnd" cx="200" cy="630" r="12"/>
<text class="pnum pnum-d" x="200" y="630">39</text>
<text class="plbl lbl-l lbl-alt" x="176" y="630">GND</text>
<circle class="p-off" cx="320" cy="630" r="12"/>
<text class="pnum pnum-d" x="320" y="630">40</text>
<text class="plbl lbl-r lbl-off" x="344" y="630">GPIO21</text>
<!-- pin1 hint -->
<text class="cap-svg" x="260" y="662" style="font-size:11px;">■ square marker = pin 1 (relative to board orientation)</text>
</svg>
<div class="legend">
<span><i class="sw pwr"></i>3.3V power — pin 1</span>
<span><i class="sw i2c"></i>I2C SDA/SCL — pins 3·5</span>
<span><i class="sw gnd"></i>GND (used) — pin 6</span>
<span><i class="sw altgnd"></i>Alt GND (optional) — 9·14·20·25·30·34·39</span>
<span><i class="sw off"></i>Unused pins</span>
</div>
<p class="diagram-cap">The pin numbers and signals in this diagram match the standard Raspberry Pi 4 Model B (BCM2711) 40-pin header layout.</p>
</section>
<!-- ============ 3. PINMAP TABLE ============ -->
<section>
<h2><span class="n">3</span>Pinmap Table <small>SHT30 → 40-pin header</small></h2>
<table>
<thead>
<tr><th style="width:30%">Signal</th><th style="width:24%">BCM</th><th style="width:14%">Phys pin</th><th>Notes</th></tr>
</thead>
<tbody>
<tr>
<td><b>3.3V power</b> (VCC)</td>
<td class="mono">—</td>
<td><span class="pinbadge pwr">1</span></td>
<td><span class="warn-inline">★ Must be 3.3V — do NOT connect 5V (pins 2·4)</span></td>
</tr>
<tr>
<td><b>I2C data</b> (SDA)</td>
<td class="mono">GPIO2 / SDA1</td>
<td><span class="pinbadge">3</span></td>
<td><span style="color:var(--muted)">모듈 내장 풀업 → 직결 시 불필요</span> (풀업 없는 베어 칩만 4.7kΩ→3.3V)</td>
</tr>
<tr>
<td><b>I2C clock</b> (SCL)</td>
<td class="mono">GPIO3 / SCL1</td>
<td><span class="pinbadge">5</span></td>
<td><span style="color:var(--muted)">모듈 내장 풀업 → 직결 시 불필요</span> (풀업 없는 베어 칩만 4.7kΩ→3.3V)</td>
</tr>
<tr>
<td><b>Ground</b> (GND)</td>
<td class="mono">—</td>
<td><span class="pinbadge gnd">6</span></td>
<td>Alt GND available: <span class="mono">9 · 14 · 20 · 25 · 30 · 34 · 39</span></td>
</tr>
<tr>
<td><b>Address select</b> (ADDR)</td>
<td class="mono">—</td>
<td><span class="pinbadge na">GND</span></td>
<td>ADDR → GND ⇒ <span class="mono">0x44</span> (selected) · ADDR → VDD ⇒ <span class="mono">0x45</span></td>
</tr>
</tbody>
</table>
</section>
<!-- ============ 4. SCHEMATIC SVG ============ -->
<section>
<h2><span class="n">4</span>Wiring Schematic <small>센서 모듈 ↔ 헤더 · 4선 직결(내장 풀업)</small></h2>
<svg class="svg-sch" viewBox="0 0 840 400" role="img" aria-label="SHT30 wiring schematic">
<!-- component boxes -->
<rect class="box" x="70" y="90" width="150" height="290" rx="8"/>
<rect class="box" x="640" y="90" width="150" height="290" rx="8"/>
<text class="boxtitle" x="145" y="116">SHT30 sensor module</text>
<text class="boxtitle" x="715" y="116">Pi 40-pin header</text>
<!-- SHT30 terminal labels (right side) -->
<text class="term" x="210" y="150" text-anchor="end">VCC</text>
<text class="term" x="210" y="200" text-anchor="end">SDA</text>
<text class="term" x="210" y="250" text-anchor="end">SCL</text>
<text class="term" x="210" y="305" text-anchor="end">GND</text>
<text class="term" x="210" y="350" text-anchor="end">ADDR</text>
<!-- Pi terminal labels (left side) -->
<text class="term" x="650" y="150">3V3 (pin 1)</text>
<text class="term" x="650" y="200">SDA1 (pin 3)</text>
<text class="term" x="650" y="250">SCL1 (pin 5)</text>
<text class="term" x="650" y="305">GND (pin 6)</text>
<!-- POWER wire (also 3V3 rail for pull-ups) -->
<path class="w-pwr" d="M220 150 H640"/>
<text class="wlbl" x="300" y="140" fill="#b02a2a">Power 3.3V</text>
<!-- GND wire -->
<path class="w-gnd" d="M220 305 H640"/>
<text class="wlbl" x="300" y="322" fill="#2b3541">Ground GND</text>
<!-- SDA wire (direct, no hop — module has on-board pull-ups) -->
<path class="w-i2c" d="M220 200 H640"/>
<text class="wlbl" x="300" y="216" fill="#155a9c">SDA → GPIO2</text>
<!-- SCL wire -->
<path class="w-i2c" d="M220 250 H640"/>
<text class="wlbl" x="300" y="266" fill="#155a9c">SCL → GPIO3</text>
<!-- ADDR -> GND -->
<path class="w-addr" d="M220 350 H300 V305"/>
<text class="wlbl" x="228" y="368" fill="#3b444d">ADDR → GND = 0x44</text>
<circle class="jn" cx="300" cy="305" r="4"/>
<!-- Purchased part is a breakout module with on-board pull-ups → no external resistors (direct 4-wire) -->
<text x="430" y="282" text-anchor="middle" font-size="12" font-weight="700" fill="#2b8a3e">모듈 내장 풀업 · 외부 저항 불필요 (4선 직결)</text>
</svg>
<p class="sch-note">
구매품은 온보드 풀업이 있는 <b>SHT30 브레이크아웃 모듈</b>이라 외부 풀업 저항이 필요 없다.
VCC·GND·SDA·SCL 4선을 헤더에 직결한다. (풀업 없는 베어 SHT30 칩을 쓸 때만 SDA·SCL에 4.7kΩ×2 → 3.3V 를 추가한다.)
</p>
</section>
<!-- ============ 5. ELECTRICAL NOTES ============ -->
<section>
<h2><span class="n">5</span>Electrical Design · Cautions</h2>
<div class="warn">
<svg class="ic" viewBox="0 0 24 24" aria-hidden="true">
<path d="M12 2 L23 21 H1 Z" fill="#ffe3e3" stroke="#e03131" stroke-width="1.6" stroke-linejoin="round"/>
<line x1="12" y1="9" x2="12" y2="15" stroke="#e03131" stroke-width="2.2" stroke-linecap="round"/>
<circle cx="12" cy="18" r="1.4" fill="#e03131"/>
</svg>
<div>
<h3>Critical Warning — On the Pi it MUST be 3.3V</h3>
<p>Connect the SHT30's <b>VCC to physical pin 1 (3.3V)</b>.
<b>Do NOT connect 5V (pins 2·4) on the Pi</b> — the SHT30 module itself tolerates 2.4–5.5V, but
powering it with 5V pulls the SDA/SCL lines up to 5V as well, which <b>damages the 3.3V-only Pi GPIO</b>.
Double-check the pin numbers before wiring.</p>
</div>
</div>
<ul class="notes">
<li><b>I2C pull-ups:</b> Connect a 4.7kΩ pull-up resistor on each of SDA and SCL to 3.3V. Can be omitted if built into the sensor module.</li>
<li><b>Address setting:</b> ADDR → GND gives <code>0x44</code> (default), ADDR → VDD gives <code>0x45</code>. Must match the <code>I2C_ADDR</code> value in <code>config.py</code>.</li>
<li><b>I2C bus:</b> Uses bus 1. I2C must be enabled after boot (<code>raspi-config</code> or <code>dtparam=i2c_arm=on</code>).</li>
<li><b>Wiring length:</b> Short cables are recommended for I2C. Long cables may cause communication errors or require adjusting the pull-up values.</li>
<li><b>Role split:</b> This node only reports readings to the server every 5 minutes. High/low temperature and high/low humidity <b>threshold decisions and SMS dispatch are done by the server</b>.</li>
<li><b>Config file:</b> <code>raspberry_pi4_sht30/config.py</code> (<code>I2C_BUS=1</code>, <code>I2C_ADDR=0x44</code>). Per-device values are overridden in <code>config_local.py</code>.</li>
</ul>
<div class="cmd">
<span class="cm"># Check I2C connection (OK if 0x44 appears in the grid)</span>
$ i2cdetect -y 1
0 1 2 3 4 5 6 7 8 9 a b c d e f
40: -- -- -- -- <span class="ok">44</span> -- -- -- -- -- -- -- -- -- -- --
</div>
</section>
<!-- ============ 6. INSTALL CHECKLIST ============ -->
<section>
<h2><span class="n">6</span>Installation Checklist</h2>
<ol class="check">
<li><span class="num"></span><span class="cbox"></span><span class="txt">Do wiring work with <b>power disconnected</b> (no hot-plugging)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Connect VCC → physical pin 1 (3.3V) — re-verify it is <b>NOT a 5V pin (2·4)</b></span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Connect GND → physical pin 6 (or 9·14·20·25·30·34·39 for alt GND)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Connect SDA → pin 3 (GPIO2), SCL → pin 5 (GPIO3)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Connect 4.7kΩ ×2 pull-up resistors from SDA·SCL → 3.3V (omit if built into module)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Verify ADDR → GND (address 0x44 selected)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Re-check all wiring, then power up the Pi</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Verify I2C is enabled (raspi-config / dtparam=i2c_arm=on)</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Run <code>i2cdetect -y 1</code> → confirm <code>0x44</code> is shown</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Verify I2C_BUS=1, I2C_ADDR=0x44 in config.py / config_local.py</span></li>
<li><span class="num"></span><span class="cbox"></span><span class="txt">Check measurement log and server reception (5-min reporting OK)</span></li>
</ol>
</section>
<footer>
Temp/Humidity Node · Pi-B (sensor_id=2, Site 1 / Server Room) · SHT30 I2C wiring doc — for on-site printing
</footer>
</div>
</body>
</html>