TL-DR
docker ps --no-trunc
และdocker inspect CONTAINER
จัดเตรียม entrypoint ที่ดำเนินการเพื่อเริ่มคอนเทนเนอร์ตามคำสั่งที่ส่งไปยัง แต่อาจพลาดบางส่วนเช่น${ANY_VAR}
เนื่องจากตัวแปรสภาวะแวดล้อมคอนเทนเนอร์ไม่ถูกพิมพ์ตามที่ได้รับการแก้ไข
ที่จะเอาชนะนั้นdocker inspect CONTAINER
มีความได้เปรียบเพราะมันยังช่วยให้สามารถดึงตัวแปร env แยกต่างหากและค่าของพวกเขาที่กำหนดไว้ในภาชนะจากConfig.Env
คุณสมบัติ
docker ps
และdocker inspect
ให้ข้อมูลเกี่ยวกับจุดเข้าใช้งานและคำสั่ง บ่อยครั้งที่เป็น wrapper entrypoint script ( .sh
) และไม่ใช่โปรแกรม "ของจริง" ที่เริ่มต้นโดยคอนเทนเนอร์ ในการรับข้อมูลเกี่ยวกับสิ่งนั้นขอข้อมูลกระบวนการด้วยps
หรือ/proc/1/cmdline
ช่วย
1) docker ps --no-trunc
มันพิมพ์จุดเข้าใช้งานและคำสั่งดำเนินการสำหรับภาชนะที่ใช้งานทั้งหมด ในขณะที่มันพิมพ์คำสั่งที่ส่งผ่านไปยังจุดเข้าใช้งาน (ถ้าเราผ่านนั้น) มันไม่แสดงค่าของตัวแปร env นักเทียบท่า (เช่น$FOO
หรือ${FOO}
)
หากคอนเทนเนอร์ของเราใช้ตัวแปร env มันอาจไม่เพียงพอ
ตัวอย่างเช่นเรียกใช้คอนเทนเนอร์อัลไพน์:
docker run --name alpine-example -e MY_VAR=/var alpine:latest sh -c 'ls $MY_VAR'
เมื่อใช้นักเทียบท่า -ps เช่น:
นักเทียบท่า ps -a - ชื่อตัวกรอง = อัลไพน์ตัวอย่าง - no-trunc
มันพิมพ์:
รหัสภาพภาชนะบรรจุคำสั่งสร้างชื่อพอร์ตสถานะ
5b064a6de6d8417 ... อัลไพน์: ล่าสุด "sh -c 'ls $ MY_VAR'" 2 นาทีที่ผ่านมาออกจาก (0) 2 นาทีที่ผ่านมาตัวอย่างอัลไพน์
เราเห็นคำสั่งที่ส่งผ่านไปยังจุดเข้าใช้งานsh -c 'ls $MY_VAR'
แต่$MY_VAR
ไม่สามารถแก้ไขได้
2) docker inspect CONTAINER
เมื่อเราตรวจสอบคอนเทนเนอร์อัลไพน์ตัวอย่าง:
docker inspect alpine-example | grep -4 Cmd
คำสั่งนั้นอยู่ที่นั่น แต่เรายังไม่เห็นค่าตัวแปร env:
"Cmd": [
"sh",
"-c",
"ls $MY_VAR"
],
ในความเป็นจริงเราไม่สามารถเห็นตัวแปรสอดแทรกด้วยคำสั่งนักเทียบท่าเหล่านี้
ในขณะที่เป็นการแลกเปลี่ยนเราสามารถแสดงทั้งคำสั่งและตัวแปร env สำหรับคอนเทนเนอร์ที่มีการตรวจสอบนักเทียบท่า:
docker inspect alpine-example | grep -4 -E "Cmd|Env"
ภาพพิมพ์นั้น:
"Env": [
"MY_VAR=/var",
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": [
"sh",
"-c",
"ls $MY_VAR"
]
วิธีที่นักเทียบท่ามากขึ้นคือการใช้--format
แฟล็กของdocker inspect
ที่อนุญาตให้ระบุแอ็ตทริบิวต์ JSON เพื่อแสดงผล:
docker inspect --format '{{.Name}} {{.Config.Cmd}} {{ (.Config.Env) }}' alpine-example
ผลลัพธ์นั้น:
/ alpine-example [sh -c ls $ MY_VAR] [MY_VAR = / var PATH = / usr / local / sbin: / usr / local / bin: / usr / sbin: / usr / bin: / sbin: / bin]
3) ดึงข้อมูลกระบวนการที่เริ่มต้นจากตัวคอนเทนเนอร์เพื่อเรียกใช้คอนเทนเนอร์
จุดเข้าใช้งานและคำสั่งที่เรียกใช้งานโดยนักเทียบท่าอาจเป็นประโยชน์ แต่ในบางกรณีมันไม่เพียงพอเพราะนั่นเป็น "สคริปต์" wrapper entrypoint ( .sh
) ที่รับผิดชอบในการเริ่มกระบวนการจริง / แกน
ตัวอย่างเช่นเมื่อใช้ภาชนะ Nexus "sh -c ${SONATYPE_DIR}/start-nexus-repository-manager.sh"
คำสั่งดำเนินการและการแสดงเพื่อเรียกใช้ภาชนะที่เป็น
สำหรับ PostgreSQL "docker-entrypoint.sh postgres"
ที่เป็น
docker exec CONTAINER ps aux
หากต้องการข้อมูลเพิ่มเติมเราสามารถดำเนินการเกี่ยวกับภาชนะที่ทำงาน
มันอาจพิมพ์กระบวนการอื่น ๆ ที่อาจไม่สนใจเรา
ในการ จำกัด กระบวนการเริ่มต้นที่เปิดโดย entrypoint เราสามารถทำ:
docker exec CONTAINER ps -1
ฉันระบุ1
เพราะกระบวนการที่ดำเนินการโดยจุดเข้าใช้งานนั้นโดยทั่วไปเป็นกระบวนการที่มี1
ID
หากไม่มีps
เรายังคงสามารถค้นหาข้อมูลใน/proc/1/cmdline
(ใน Linux distros ส่วนใหญ่ แต่ไม่ใช่ทั้งหมด) ตัวอย่างเช่น :
docker exec CONTAINER cat /proc/1/cmdline | sed -e "s/\x00/ /g"; echo
หากเรามีการเข้าถึงโฮสต์นักเทียบท่าที่เริ่มต้นคอนเทนเนอร์ทางเลือกอื่นเพื่อรับคำสั่งทั้งหมดของกระบวนการที่ดำเนินการโดยจุดเข้าใช้งานคือ:: execute ps -PID
โดย PID เป็นกระบวนการโลคัลที่สร้างโดย Docker daemon เพื่อเรียกใช้คอนเทนเนอร์เช่น:
ps -$(docker container inspect --format '{{.State.Pid}}' CONTAINER)
การจัดรูปแบบที่ใช้งานง่ายด้วย ps docker
docker ps --no-trunc
ไม่ใช่เรื่องง่ายที่จะอ่าน
การระบุคอลัมน์ที่จะพิมพ์และในรูปแบบตารางอาจทำให้ดีขึ้น:
docker ps --no-trunc --format "table{{.Names}}\t{{.CreatedAt}}\t{{.Command}}"
สร้างนามแฝงอาจช่วยได้:
alias dps='docker ps --no-trunc --format "table{{.Names}}\t{{.CreatedAt}}\t{{.Command}}"'