当前位置: 首页 > news >正文

如何使用 Dockerfile 创建自定义镜像?

使用Dockerfile创建自定义镜像是 Docker 的核心功能之一。Dockerfile是一个包含了一系列构建指令的文本文件,Docker 会根据这些指令自动构建出镜像。

以下是创建自定义镜像的完整步骤和最佳实践:

1. 创建项目目录

首先,创建一个专门的目录来存放你的应用代码和Dockerfile

mkdirmy-appcdmy-app

2. 编写 Dockerfile

在目录中创建一个名为Dockerfile的文件(没有后缀名)。

示例:构建一个 Python Web 应用镜像

假设你有一个简单的app.py

文件结构:

my-app/ ├── Dockerfile ├── app.py └── requirements.txt

Dockerfile 内容:

# 1. 指定基础镜像 (FROM) # 使用官方 Python 3.9 轻量级版本 FROM python:3.9-slim # 2. 设置工作目录 (WORKDIR) # 在容器内创建 /app 目录,并将后续命令的工作目录设为此 WORKDIR /app # 3. 复制依赖文件 (COPY) # 先复制 requirements.txt,利用 Docker 缓存层优化构建速度 COPY requirements.txt . # 4. 安装依赖 (RUN) # 在构建镜像时执行安装命令 RUN pip install --no-cache-dir -r requirements.txt # 5. 复制应用代码 (COPY) # 将当前目录下的所有文件复制到容器的 /app 目录 COPY . . # 6. 暴露端口 (EXPOSE) # 告知 Docker 容器运行时监听该端口(仅文档说明,不自动转发) EXPOSE 8000 # 7. 定义容器启动命令 (CMD) # 容器启动时执行的命令 CMD ["python", "app.py"]
常用指令详解:
指令作用示例
FROM指定基础镜像FROM ubuntu:20.04
RUN构建时执行命令(如安装软件)RUN apt-get update
COPY将本地文件复制到镜像COPY . /app
ADD类似 COPY,但支持解压和 URLADD file.tar.gz /app/
WORKDIR设置工作目录WORKDIR /usr/src/app
ENV设置环境变量ENV APP_ENV=production
EXPOSE声明监听端口EXPOSE 8080
CMD容器启动时的默认命令CMD ["python", "main.py"]
ENTRYPOINT配置容器可执行主程序ENTRYPOINT ["./start.sh"]
USER指定运行用户USER appuser

3. 构建镜像

使用docker build命令根据Dockerfile构建镜像。

# 语法:docker build -t <镜像名称>:<标签> <构建上下文路径>dockerbuild-tmy-python-app:1.0.
  • -t: 指定镜像的标签(名称:版本)。
  • .: 表示构建上下文是当前目录(Docker 会查找当前目录下的 Dockerfile)。

构建过程:
Docker 会逐行执行Dockerfile中的指令。每一步都会生成一个新的层(Layer)。如果某一步没有变化,Docker 会直接使用缓存层,从而加快构建速度。

4. 验证镜像

构建完成后,查看本地镜像列表:

dockerimages

你应该能看到名为my-python-app,标签为1.0的镜像。

5. 运行容器

使用构建好的镜像启动容器:

# 启动容器并映射端口dockerrun-d-p8000:8000--namemy-running-app my-python-app:1.0
  • -d: 后台运行。
  • -p 8000:8000: 将宿主机的 8000 端口映射到容器的 8000 端口。
  • --name: 给容器起个名字。

6. 最佳实践与优化技巧

  1. 利用缓存层(Layer Caching)

    • 错误做法:先COPY . .RUN pip install。只要代码改了一个字符,缓存失效,需要重新安装所有依赖。
    • 正确做法:先COPY requirements.txtRUN pip install,最后COPY . .。只有依赖文件变化时才会重新安装。
  2. 使用.dockerignore文件
    在构建上下文排除不必要的文件(如.git,node_modules,__pycache__, 本地日志等),可以减小构建上下文大小,加快构建速度,并避免敏感信息泄露。

    # .dockerignore 示例 .git __pycache__ *.log venv .env
  3. 多阶段构建(Multi-stage Builds)
    用于减小最终镜像体积。例如,在构建 Java 或 Go 应用时,第一阶段使用包含编译器的重型镜像进行编译,第二阶段只复制编译好的二进制文件到轻量级运行镜像中。

    # 构建阶段 FROM maven:3.8 AS build WORKDIR /app COPY . . RUN mvn clean package # 运行阶段 FROM openjdk:11-jre-slim WORKDIR /app COPY --from=build /app/target/app.jar app.jar CMD ["java", "-jar", "app.jar"]
  4. 避免使用latest标签
    FROM指令中尽量指定具体版本号(如python:3.9-slim),而不是latest,以保证构建的可重复性和稳定性。

  5. 清理缓存
    RUN命令中,如果安装了包,最好在同一层中清理包管理器缓存,避免镜像体积膨胀。

    RUN apt-get update && apt-get install -y curl && rm -rf /var/lib/apt/lists/*
http://www.jsqmd.com/news/557850/

相关文章:

  • 3个维度突破股票数据获取难题:MOOTDX量化分析实战指南
  • 【紧急通知】Python 3.14 JIT默认profile已触发AWS Lambda冷启动恶化阈值!立即执行这4项低成本开关校准
  • 从‘发动鸡’到‘三元催化’:手把手解决中文NER中的口语化与OOV难题(含代码示例)
  • 3款电脑实用神器合集,视频无损分割不压缩、视障友好屏幕阅读器、图片批量一键加水印,日常办公剪辑修图全搞定
  • Zemax新手避坑指南:从零开始搞定一个F/4的单透镜设计(附完整操作截图)
  • OpenClaw多模型切换指南:百川2-13B与Qwen3-32B的自动化任务对比
  • 高效Switch游戏安装:Awoo Installer多源部署技术深度解析
  • 隐式建模的革新:GemPy如何重新定义三维地质结构可视化
  • 003、NumPy与科学计算基础:从一次内存泄漏调试说起
  • ComfyUI视频合成节点修复指南:从诊断到优化的完整解决方案
  • QT6在Ubuntu20.4上的避坑指南:为什么你的安装总是失败?
  • STM32CubeMX + ESP8266 避坑实录:从硬件接线到TCP通信,我踩过的坑你别再踩
  • EtherCAT主站结构体深度游:ec_master_t里每个成员都是干嘛的?
  • Qwen3-32B量化新方案:w16a16s精度零损失揭秘
  • ncmdumpGUI+解决网易云音乐NCM文件跨设备播放痛点
  • Cadence Virtuoso IC617版图寄生参数提取与后仿真的实战避坑指南
  • OpenClaw+GLM-4.7-Flash:自动化会议纪要生成实践
  • 3步掌握ArrayFire:零基础实现GPU加速计算
  • 2026西南基建定制输送带优质厂家推荐榜:耐高温输送带/辊道输送机/输送带托辊/输送带生产厂家/输送机厂家/食品输送带/选择指南 - 优质品牌商家
  • OpenClaw技能开发入门:为百川2-13B模型定制专属自动化模块
  • Nomic-Embed-Text-V2-MoE代码实战:Python爬虫数据向量化处理
  • 用YOLOv11-l和YOLOv11-n实测路面裂缝检测:300轮训练后,哪个模型更适合你的无人机巡检项目?
  • 三坐标测量仪在汽车制造中的实战应用:从发动机缸体到斜油孔测量全解析
  • 中关村论坛重磅发布十五项脑机接口成果
  • 3DS GBA模拟器:利用open_agb_firm实现原生硬件加速的复古游戏体验
  • 深入中科蓝讯蓝牙SDK:如何利用xcfg.xm自定义配置并实现工具与代码联动
  • ChatGPT/DeepSeek写的论文降AI率教程:分步骤解决高AI率问题
  • 智能座舱仪表屏背后的信号之旅:从SOC的MIPI DSI到LCD面板的LVDS,详解MAX96755/52 SerDes链路
  • SkyWalking 8.1.0 UI 魔改实战:如何从源码入手,打造一个只保留追踪功能的极简监控面板
  • 电动汽车车队虚拟发电厂的强化学习控制策略探索