Kubernetes 中的启动命令定义了容器启动时运行的主要可执行文件。它们对应于 Kubernetes Pod 规范中的 command
字段,并覆盖容器镜像中定义的默认 ENTRYPOINT 指令。启动命令提供了对容器内运行进程的完全控制。
启动命令是:
理解 Docker 指令与 Kubernetes 字段之间的关系:
Docker | Kubernetes | 作用 |
---|---|---|
ENTRYPOINT | command | 定义可执行文件 |
CMD | args | 提供默认参数 |
# Dockerfile 示例
FROM ubuntu:20.04
ENTRYPOINT ["/usr/bin/myapp"]
CMD ["--config=/etc/default.conf"]
# Kubernetes 覆盖示例
apiVersion: v1
kind: Pod
spec:
containers:
- name: myapp
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["--config=/etc/custom.conf", "--debug"]
场景 | Docker 镜像 | Kubernetes 规范 | 最终命令 |
---|---|---|---|
默认 | ENTRYPOINT + CMD | (无) | ENTRYPOINT + CMD |
仅覆盖 args | ENTRYPOINT + CMD | args: ["new-args"] | ENTRYPOINT + new-args |
仅覆盖 command | ENTRYPOINT + CMD | command: ["new-cmd"] | new-cmd |
同时覆盖 command 和 args | ENTRYPOINT + CMD | command: ["new-cmd"] args: ["new-args"] | new-cmd + new-args |
使用相同基础镜像运行不同应用:
apiVersion: v1
kind: Pod
metadata:
name: web-server
spec:
containers:
- name: nginx
image: ubuntu:20.04
command: ["/usr/sbin/nginx"]
args: ["-g", "daemon off;", "-c", "/etc/nginx/nginx.conf"]
覆盖默认命令启动 shell 进行调试:
apiVersion: v1
kind: Pod
metadata:
name: debug-pod
spec:
containers:
- name: debug
image: myapp:latest
command: ["/bin/bash"]
args: ["-c", "sleep 3600"]
在启动主应用前运行自定义初始化:
apiVersion: v1
kind: Pod
spec:
containers:
- name: app
image: myapp:latest
command: ["/bin/sh"]
args:
- "-c"
- |
echo "Initializing application..."
/scripts/init.sh
echo "Starting main application..."
exec /usr/bin/myapp --config=/etc/app.conf
同一镜像用于不同用途:
# Web 服务器
apiVersion: apps/v1
kind: Deployment
metadata:
name: web
spec:
template:
spec:
containers:
- name: web
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["server", "--port=8080"]
---
# 后台工作进程
apiVersion: apps/v1
kind: Deployment
metadata:
name: worker
spec:
template:
spec:
containers:
- name: worker
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["worker", "--queue=tasks"]
---
# 数据库迁移
apiVersion: batch/v1
kind: Job
metadata:
name: migrate
spec:
template:
spec:
containers:
- name: migrate
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["migrate", "--up"]
restartPolicy: Never
# 完全覆盖命令
kubectl run debug --image=nginx:alpine --command -- /bin/sh -c "sleep 3600"
# 运行交互式 shell
kubectl run -it debug --image=ubuntu:20.04 --restart=Never --command -- /bin/bash
# 自定义应用启动
kubectl run myapp --image=myapp:latest --command -- /usr/local/bin/start.sh --config=/etc/app.conf
# 一次性任务
kubectl run task --image=busybox --restart=Never --command -- /bin/sh -c "echo 'Task completed'"
# 创建带自定义命令的 job
kubectl create job backup --image=postgres:13 --dry-run=client -o yaml -- pg_dump -h db.example.com mydb > backup.yaml
# 应用 job
kubectl apply -f backup.yaml
apiVersion: v1
kind: Pod
metadata:
name: complex-init
spec:
containers:
- name: app
image: myapp:latest
command: ["/bin/bash"]
args:
- "-c"
- |
set -e
echo "Step 1: Checking dependencies..."
/scripts/check-deps.sh
echo "Step 2: Setting up configuration..."
/scripts/setup-config.sh
echo "Step 3: Running database migrations..."
/scripts/migrate.sh
echo "Step 4: Starting application..."
exec /usr/bin/myapp --config=/etc/app/config.yaml
volumeMounts:
- name: scripts
mountPath: /scripts
- name: config
mountPath: /etc/app
volumes:
- name: scripts
configMap:
name: init-scripts
defaultMode: 0755
- name: config
configMap:
name: app-config
apiVersion: apps/v1
kind: Deployment
metadata:
name: conditional-app
spec:
template:
spec:
containers:
- name: app
image: myapp:latest
command: ["/bin/sh"]
args:
- "-c"
- |
if [ "$APP_MODE" = "worker" ]; then
exec /usr/bin/myapp worker --queue=$QUEUE_NAME
elif [ "$APP_MODE" = "scheduler" ]; then
exec /usr/bin/myapp scheduler --interval=60
else
exec /usr/bin/myapp server --port=8080
fi
env:
- name: APP_MODE
value: "server"
- name: QUEUE_NAME
value: "default"
# ✅ 正确的信号处理
apiVersion: v1
kind: Pod
spec:
containers:
- name: app
image: myapp:latest
command: ["/bin/bash"]
args:
- "-c"
- |
# 捕获 SIGTERM 实现优雅关闭
trap 'echo "Received SIGTERM, shutting down gracefully..."; kill -TERM $PID; wait $PID' TERM
# 后台启动主应用
/usr/bin/myapp --config=/etc/app.conf &
PID=$!
# 等待进程结束
wait $PID
apiVersion: v1
kind: Pod
spec:
containers:
- name: app
image: myapp:latest
command: ["/bin/bash"]
args:
- "-c"
- |
set -euo pipefail # 出错、未定义变量或管道失败时退出
log() {
echo "[$(date '+%Y-%m-%d %H:%M:%S')] $*" >&2
}
log "Starting application initialization..."
if ! /scripts/health-check.sh; then
log "ERROR: Health check failed"
exit 1
fi
log "Starting main application..."
exec /usr/bin/myapp --config=/etc/app.conf
# ✅ 以非 root 用户运行
apiVersion: v1
kind: Pod
spec:
securityContext:
runAsNonRoot: true
runAsUser: 1000
runAsGroup: 1000
containers:
- name: app
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["--config=/etc/app.conf"]
securityContext:
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
capabilities:
drop:
- ALL
apiVersion: v1
kind: Pod
spec:
containers:
- name: app
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["--config=/etc/app.conf"]
resources:
requests:
memory: "64Mi"
cpu: "250m"
limits:
memory: "128Mi"
cpu: "500m"
apiVersion: v1
kind: Pod
spec:
initContainers:
- name: setup
image: busybox
command: ["/bin/sh"]
args:
- "-c"
- |
echo "Setting up shared data..."
mkdir -p /shared/data
echo "Setup complete" > /shared/data/status
volumeMounts:
- name: shared-data
mountPath: /shared
containers:
- name: app
image: myapp:latest
command: ["/bin/sh"]
args:
- "-c"
- |
while [ ! -f /shared/data/status ]; do
echo "Waiting for setup to complete..."
sleep 1
done
echo "Starting application..."
exec /usr/bin/myapp
volumeMounts:
- name: shared-data
mountPath: /shared
volumes:
- name: shared-data
emptyDir: {}
apiVersion: v1
kind: Pod
spec:
containers:
# 主应用
- name: app
image: myapp:latest
command: ["/usr/bin/myapp"]
args: ["--config=/etc/app.conf"]
# 日志收集 sidecar
- name: log-shipper
image: fluent/fluent-bit:latest
command: ["/fluent-bit/bin/fluent-bit"]
args: ["--config=/fluent-bit/etc/fluent-bit.conf"]
# 指标导出 sidecar
- name: metrics
image: prom/node-exporter:latest
command: ["/bin/node_exporter"]
args: ["--path.rootfs=/host"]
# 备份 job
apiVersion: batch/v1
kind: Job
metadata:
name: database-backup
spec:
template:
spec:
containers:
- name: backup
image: postgres:13
command: ["/bin/bash"]
args:
- "-c"
- |
set -e
echo "Starting backup at $(date)"
pg_dump -h $DB_HOST -U $DB_USER $DB_NAME > /backup/dump-$(date +%Y%m%d-%H%M%S).sql
echo "Backup completed at $(date)"
env:
- name: DB_HOST
value: "postgres.example.com"
- name: DB_USER
value: "backup_user"
- name: DB_NAME
value: "myapp"
volumeMounts:
- name: backup-storage
mountPath: /backup
restartPolicy: Never
volumes:
- name: backup-storage
persistentVolumeClaim:
claimName: backup-pvc
启动命令为 Kubernetes 中容器执行提供了完全的控制。通过理解如何正确配置和使用启动命令,您可以创建灵活、可维护且健壮的容器化应用,以满足您的特定需求。