Docker 瀹瑰櫒鍖栭儴缃叉渶浣冲疄璺?/title> <link href="https://fonts.googleapis.com/css2?family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet"> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/styles/github.min.css">\n <script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/highlight.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/languages/dockerfile.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.7.0/languages/yaml.min.js"></script> <style> /* 鍩虹鏍峰紡鍙橀噺瀹氫箟 */ :root { --primary-color: #4361ee; --secondary-color: #3a0ca3; --accent-color: #f72585; --text-color: #333333; --background-color: #ffffff; --card-background: #f8f9fa; --border-color: #e9ecef; --code-background: #f6f8fa; --shadow: 0 2px 8px rgba(0, 0, 0, 0.08); --radius: 8px; --transition: all 0.2s ease; } * { margin: 0; padding: 0; box-sizing: border-box; } html { scroll-behavior: smooth; } body { font-family: 'Noto Sans SC', 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; background-color: var(--background-color); color: var(--text-color); line-height: 1.6; font-size: 16px; } /* 涓诲鍣?*/ .container { max-width: 800px; margin: 0 auto; padding: 2rem 1.5rem; } /* 鏍囬鏍峰紡 */ h1 { color: var(--primary-color); font-size: 2rem; font-weight: 700; margin-bottom: 1.5rem; text-align: center; padding-bottom: 1rem; border-bottom: 2px solid var(--border-color); } h2 { color: var(--secondary-color); font-size: 1.5rem; font-weight: 600; margin: 2rem 0 1rem; padding-bottom: 0.5rem; border-bottom: 1px solid var(--border-color); } h3 { color: var(--text-color); font-size: 1.2rem; font-weight: 500; margin: 1.5rem 0 0.8rem; } /* 娈佃惤鍜屾枃鏈?*/ p { margin: 1rem 0; text-align: justify; } /* 鍒楄〃鏍峰紡 */ ul, ol { margin: 1rem 0; padding-left: 2rem; } li { margin: 0.5rem 0; } /* 浠g爜鏍峰紡 */ pre { background-color: var(--code-background); border-radius: var(--radius); padding: 1rem; overflow-x: auto; margin: 1.5rem 0; box-shadow: var(--shadow); } code { font-family: 'Consolas', 'Monaco', 'Courier New', monospace; font-size: 0.9rem; color: var(--secondary-color); } pre code { color: var(--text-color); } /* 鍗$墖鏍峰紡 */ .card { background-color: var(--card-background); border-radius: var(--radius); padding: 1.5rem; margin: 1.5rem 0; box-shadow: var(--shadow); transition: var(--transition); } .card:hover { box-shadow: 0 4px 12px rgba(0, 0, 0, 0.12); transform: translateY(-2px); } /* 鎻愮ず妗嗘牱寮?*/ .tip { background-color: rgba(67, 97, 238, 0.1); border-left: 4px solid var(--primary-color); padding: 1rem; margin: 1.5rem 0; border-radius: 0 var(--radius) var(--radius) 0; } /* 浠g爜楂樹寒 */ .hljs { background: var(--code-background) !important; } /* 鍝嶅簲寮忚璁?*/ @media (max-width: 768px) { .container { padding: 1.5rem 1rem; } h1 { font-size: 1.8rem; } h2 { font-size: 1.3rem; } h3 { font-size: 1.1rem; } } /* 澶撮儴瀵艰埅 */ header { background-color: var(--background-color); border-bottom: 1px solid var(--border-color); padding: 1rem 0; margin-bottom: 2rem; box-shadow: var(--shadow); } .header-container { max-width: 800px; margin: 0 auto; padding: 0 1.5rem; display: flex; justify-content: space-between; align-items: center; } .header-title { font-size: 1.2rem; font-weight: 700; color: var(--primary-color); } .back-link { color: var(--text-color); text-decoration: none; font-size: 0.9rem; transition: var(--transition); padding: 0.5rem 1rem; border-radius: var(--radius); border: 1px solid var(--border-color); } .back-link:hover { background-color: var(--primary-color); color: white; border-color: var(--primary-color); } /* 鍝嶅簲寮忓ご閮ㄨ璁?*/ @media (max-width: 768px) { .header-container { padding: 0 1rem; } .header-title { font-size: 1.1rem; } .back-link { padding: 0.4rem 0.8rem; font-size: 0.85rem; } } </style> </head> <body> <!-- 澶撮儴瀵艰埅 --> <header> <div class="header-container"> <div class="header-title">Docker鏁欑▼</div> <a href="../article.html" class="back-link">杩斿洖鏂囩珷鍒楄〃</a> </div> </header> <div class="container"> <h1>Docker 瀹瑰櫒鍖栭儴缃叉渶浣冲疄璺?/h1> <p>Docker 鏄竴绉嶆祦琛岀殑瀹瑰櫒鍖栨妧鏈紝鍏佽寮€鍙戣€呭皢搴旂敤绋嬪簭鍙婂叾渚濊禆椤规墦鍖呭埌涓€涓交閲忕骇銆佸彲绉绘鐨勫鍣ㄤ腑銆傛湰鏂囧皢浠嬬粛 Docker 瀹瑰櫒鍖栭儴缃茬殑鏈€浣冲疄璺碉紝甯姪寮€鍙戣€呮瀯寤烘洿楂樻晥銆佹洿鍙潬鐨勫鍣ㄥ寲搴旂敤銆?/p> <h2>1. Dockerfile 鏈€浣冲疄璺?/h2> <h3>1.1 浣跨敤瀹樻柟鍩虹闀滃儚</h3> <p>浣跨敤瀹樻柟鍩虹闀滃儚鍙互纭繚闀滃儚鐨勫畨鍏ㄦ€у拰鍙潬鎬с€?/p> <pre><code class="dockerfile"># 濂界殑鍋氭硶锛氫娇鐢ㄥ畼鏂瑰熀纭€闀滃儚 FROM node:16-alpine # 涓嶅ソ鐨勫仛娉曪細浣跨敤闈炲畼鏂规垨鏈煡鏉ユ簮鐨勯暅鍍? FROM someuser/node:16</code></pre> <h3>1.2 浣跨敤鐗瑰畾鐗堟湰鏍囩</h3> <p>閬垮厤浣跨敤 `latest` 鏍囩锛屽洜涓哄畠鍙兘瀵艰嚧涓嶅彲棰勬祴鐨勬瀯寤虹粨鏋溿€?/p> <pre><code class="dockerfile"># 濂界殑鍋氭硶锛氫娇鐢ㄧ壒瀹氱増鏈爣绛? FROM node:16.14.0-alpine # 涓嶅ソ鐨勫仛娉曪細浣跨敤 latest 鏍囩 FROM node:latest</code></pre> <h3>1.3 鏈€灏忓寲闀滃儚澶у皬</h3> <p>浣跨敤 Alpine 鐗堟湰鐨勫熀纭€闀滃儚锛屽噺灏戦暅鍍忓ぇ灏忋€?/p> <pre><code class="dockerfile"># 濂界殑鍋氭硶锛氫娇鐢?Alpine 鐗堟湰 FROM node:16-alpine # 涓嶅ソ鐨勫仛娉曪細浣跨敤瀹屾暣鐗堟湰 FROM node:16</code></pre> <h3>1.4 鍚堢悊浣跨敤灞傜紦瀛?/h3> <p>灏嗕笉缁忓父鍙樺寲鐨勬寚浠ゆ斁鍦ㄥ墠闈紝鍏呭垎鍒╃敤 Docker 鐨勫眰缂撳瓨銆?/p> <pre><code class="dockerfile"># 濂界殑鍋氭硶锛氬厛瀹夎渚濊禆锛屽啀澶嶅埗浠g爜 FROM node:16-alpine WORKDIR /app # 澶嶅埗 package.json 鍜?package-lock.json COPY package*.json ./ # 瀹夎渚濊禆 RUN npm install # 澶嶅埗搴旂敤浠g爜 COPY . . # 鍚姩搴旂敤 CMD ["npm", "start"]</code></pre> <h3>1.5 娓呯悊鏋勫缓渚濊禆</h3> <p>鍦ㄦ瀯寤鸿繃绋嬩腑娓呯悊涓嶉渶瑕佺殑渚濊禆锛屽噺灏戦暅鍍忓ぇ灏忋€?/p> <pre><code class="dockerfile">FROM node:16-alpine WORKDIR /app COPY package*.json ./ # 瀹夎渚濊禆骞舵竻鐞嗙紦瀛? RUN npm install --production && npm cache clean --force COPY . . CMD ["npm", "start"]</code></pre> <h2>2. 瀹瑰櫒绠$悊鏈€浣冲疄璺?/h2> <h3>2.1 浣跨敤 Docker Compose</h3> <p>瀵逛簬澶氬鍣ㄥ簲鐢紝浣跨敤 Docker Compose 鏉ョ鐞嗐€?/p> <pre><code class="yaml">version: '3' services: web: build: . ports: - "3000:3000" depends_on: - db db: image: postgres:13-alpine environment: POSTGRES_PASSWORD: example</code></pre> <h3>2.2 鍚堢悊璁剧疆璧勬簮闄愬埗</h3> <p>涓哄鍣ㄨ缃悎鐞嗙殑璧勬簮闄愬埗锛岄伩鍏嶈祫婧愪簤鐢ㄣ€?/p> <pre><code class="yaml">version: '3' services: web: build: . ports: - "3000:3000" deploy: resources: limits: cpus: "0.5" memory: "512M" reservations: cpus: "0.25" memory: "256M"</code></pre> <h3>2.3 浣跨敤鍋ュ悍妫€鏌?/h3> <p>涓哄鍣ㄦ坊鍔犲仴搴锋鏌ワ紝纭繚瀹瑰櫒姝e父杩愯銆?/p> <pre><code class="yaml">version: '3' services: web: build: . ports: - "3000:3000" healthcheck: test: ["CMD", "curl", "-f", "http://localhost:3000/health"] interval: 30s timeout: 10s retries: 3</code></pre> <h2>3. 鏁版嵁绠$悊鏈€浣冲疄璺?/h2> <h3>3.1 浣跨敤鍗风鐞嗘暟鎹?/h3> <p>浣跨敤 Docker 鍗锋潵鎸佷箙鍖栨暟鎹紝閬垮厤鏁版嵁涓㈠け銆?/p> <pre><code class="yaml">version: '3' services: db: image: postgres:13-alpine volumes: - postgres_data:/var/lib/postgresql/data volumes: postgres_data:</code></pre> <h3>3.2 鍒嗙閰嶇疆鍜屼唬鐮?/h3> <p>浣跨敤鐜鍙橀噺鎴栭厤缃枃浠舵寕杞芥潵绠$悊閰嶇疆銆?/p> <pre><code class="yaml">version: '3' services: web: build: . ports: - "3000:3000" environment: - NODE_ENV=production - DATABASE_URL=postgres://user:password@db:5432/dbname volumes: - ./config:/app/config</code></pre> <h2>4. 瀹夊叏鎬ф渶浣冲疄璺?/h2> <h3>4.1 鏈€灏忔潈闄愬師鍒?/h3> <p>浣跨敤闈?root 鐢ㄦ埛杩愯瀹瑰櫒銆?/p> <pre><code class="dockerfile">FROM node:16-alpine # 鍒涘缓闈?root 鐢ㄦ埛 RUN adduser -D appuser # 鍒囨崲鍒伴潪 root 鐢ㄦ埛 USER appuser WORKDIR /app COPY package*.json ./ RUN npm install COPY . . CMD ["npm", "start"]</code></pre> <h3>4.2 瀹氭湡鏇存柊闀滃儚</h3> <p>瀹氭湡鏇存柊鍩虹闀滃儚锛屼慨澶嶅畨鍏ㄦ紡娲炪€?/p> <h3>4.3 鎵弿闀滃儚婕忔礊</h3> <p>浣跨敤宸ュ叿鎵弿闀滃儚涓殑瀹夊叏婕忔礊銆?/p> <pre><code class="bash"># 浣跨敤 Docker Scan 鎵弿闀滃儚 docker scan myapp:latest # 鎴栬€呬娇鐢?Trivy docker run --rm -v /var/run/docker.sock:/var/run/docker.sock aquasec/trivy image myapp:latest</code></pre> <h2>5. 閮ㄧ讲绛栫暐鏈€浣冲疄璺?/h2> <h3>5.1 浣跨敤 CI/CD 娴佺▼</h3> <p>闆嗘垚 CI/CD 娴佺▼锛屽疄鐜拌嚜鍔ㄥ寲鏋勫缓鍜岄儴缃层€?/p> <pre><code class="yaml"># GitHub Actions 绀轰緥 name: Docker Build and Push on: push: branches: [ main ] jobs: build: runs-on: ubuntu-latest steps: - uses: actions/checkout@v2 - name: Build and push Docker image uses: docker/build-push-action@v2 with: context: . push: true tags: username/myapp:latest</code></pre> <h3>5.2 浣跨敤澶氶樁娈垫瀯寤?/h3> <p>浣跨敤澶氶樁娈垫瀯寤哄噺灏戞渶缁堥暅鍍忓ぇ灏忋€?/p> <pre><code class="dockerfile"># 鏋勫缓闃舵 FROM node:16-alpine as builder WORKDIR /app COPY package*.json ./ RUN npm install COPY . . RUN npm run build # 杩愯闃舵 FROM node:16-alpine WORKDIR /app COPY --from=builder /app/package*.json ./ COPY --from=builder /app/build ./build RUN npm install --production CMD ["npm", "start"]</code></pre> <h3>5.3 钃濈豢閮ㄧ讲</h3> <p>浣跨敤钃濈豢閮ㄧ讲绛栫暐锛屽疄鐜伴浂 downtime 閮ㄧ讲銆?/p> <h2>6. 鐩戞帶鍜屾棩蹇楁渶浣冲疄璺?/h2> <h3>6.1 闆嗕腑鍖栨棩蹇楃鐞?/h3> <p>浣跨敤 ELK Stack 鎴?Graylog 绛夊伐鍏烽泦涓鐞嗘棩蹇椼€?/p> <pre><code class="yaml">version: '3' services: web: build: . logging: driver: "json-file" options: max-size: "10m" max-file: "3" elasticsearch: image: elasticsearch:7.14.0 ports: - "9200:9200" logstash: image: logstash:7.14.0 volumes: - ./logstash.conf:/etc/logstash/conf.d/logstash.conf kibana: image: kibana:7.14.0 ports: - "5601:5601" depends_on: - elasticsearch</code></pre> <h3>6.2 鐩戞帶瀹瑰櫒鍋ュ悍鐘舵€?/h3> <p>浣跨敤 Prometheus 鍜?Grafana 鐩戞帶瀹瑰櫒鍋ュ悍鐘舵€併€?/p> <div class="tip"> <strong>鎻愮ず锛?/strong> 缁撳悎浣跨敤 Docker Compose 鍜?Docker Swarm 鎴?Kubernetes锛屽彲浠ュ疄鐜版洿楂樼骇鐨勫鍣ㄧ紪鎺掑拰绠$悊銆? </div> <div class="card"> <h3>鎬荤粨</h3> <p>Docker 瀹瑰櫒鍖栭儴缃叉槸鐜颁唬搴旂敤寮€鍙戝拰閮ㄧ讲鐨勯噸瑕佸伐鍏枫€傞€氳繃鏈枃浠嬬粛鐨勬渶浣冲疄璺碉紝寮€鍙戣€呭彲浠ユ瀯寤烘洿楂樻晥銆佹洿鍙潬銆佹洿瀹夊叏鐨勫鍣ㄥ寲搴旂敤銆傚叧閿槸瑕佺悊瑙?Docker 鐨勫伐浣滃師鐞嗭紝閬靛惊鏈€浣冲疄璺碉紝骞舵牴鎹疄闄呭簲鐢ㄥ満鏅繘琛岃皟鏁淬€傞殢鐫€瀹瑰櫒鎶€鏈殑涓嶆柇鍙戝睍锛屾寔缁涔犲拰瀹炶返鏂扮殑鎶€鏈拰鏂规硶涔熸槸闈炲父閲嶈鐨勩€?/p> </div> </div> <script> // 鍒濆鍖栦唬鐮侀珮浜? document.addEventListener('DOMContentLoaded', (event) => { document.querySelectorAll('pre code').forEach((block) => { hljs.highlightBlock(block); }); }); </script> <footer> <div class="footer-content"> <p>© 2026 骞冲钩鐨勫皬鐮寸珯 鐗堟潈鎵€鏈?/p> <div class="footer-links"> <span>鐢?<a href="https://ppkjgzs.top" class="footer-link" target="_blank">骞冲钩鐨勫皬鐮寸珯</a> 鍒朵綔</span> <span class="divider">|</span> <span>浣跨敤 <span class="tech">HTML5</span>, <span class="tech">CSS3</span> 鍜?<span class="tech">Font Awesome</span> 鏋勫缓</span> <span class="divider">|</span> <a href="https://beian.miit.gov.cn/" target="_blank" class="footer-link">娴橧CP澶?025194709鍙?2</a> <span class="divider">|</span> <a href="https://beian.mps.gov.cn/#/query/webSearch?code=13020202000680" rel="noreferrer" target="_blank" class="footer-link">鍐€鍏綉瀹夊13020202000680鍙?/a> </div> </div> </footer> <style> /* 椤佃剼鏍峰紡 */ footer { background-color: #ffffff; color: var(--text-color); padding: 2rem 1rem; text-align: center; margin-top: 3rem; font-size: 0.9rem; border-top: 1px solid var(--border-color); } .footer-content { max-width: 800px; margin: 0 auto; text-align: center; } .footer-content p { text-align: center; margin-bottom: 1rem; } .footer-links { margin-top: 1rem; display: flex; flex-wrap: wrap; justify-content: center; align-items: center; gap: 1rem; font-size: 0.85rem; text-align: center; } .footer-links span { text-align: center; } .footer-link { color: var(--primary-color); text-decoration: none; } .footer-link:hover { text-decoration: underline; } .divider { color: var(--border-color); } .tech { color: var(--primary-color); font-weight: 500; } /* 椤佃剼鍝嶅簲寮忎紭鍖?*/ @media (max-width: 768px) { footer { padding: 1.5rem 1rem; font-size: 0.85rem; } .footer-links { gap: 0.8rem; font-size: 0.8rem; } } </style> </body> </html>