SSD Nodes Learn RAM 8GB — $66/ปี
คู่มือ Matt Connorโดย Matt Connor · อัปเดตเมื่อ 2026-08-01

ความแตกต่างระหว่าง docker compose stop กับ down

คำสั่ง stop เพียงหยุดคอนเทนเนอร์แต่ข้อมูลยังอยู่ ส่วน down จะลบคอนเทนเนอร์และเครือข่ายทิ้ง ทั้งคู่ไม่ลบ named volume เว้นแต่จะใช้แฟล็ก --volumes เพื่อล้างข้อมูลทั้งหมด

คำตอบโดยย่อ

docker compose stop จะหยุดการทำงานของคอนเทนเนอร์และคงข้อมูลไว้บนดิสก์ ส่วน docker compose down จะหยุดการทำงานของคอนเทนเนอร์จากนั้นจึงลบคอนเทนเนอร์และเครือข่ายที่ Compose สร้างขึ้นสำหรับโปรเจกต์นั้นทิ้งไป คำสั่งทั้งสองแบบไม่ส่งผลกระทบต่อ named volume ข้อมูลในฐานข้อมูลของคุณจะถูกลบออกก็ต่อเมื่อคุณเพิ่ม -v เข้าไป เช่นในคำสั่ง docker compose down -v ซึ่งจะลบ named volume ที่ประกาศไว้ในส่วน volumes ของไฟล์ Compose

นี่คือความแตกต่างทั้งหมดในย่อหน้าเดียว ส่วนที่เหลือของคู่มือนี้จะพิสูจน์ให้เห็นด้วย Postgres volume ที่คุณสามารถสังเกตได้ว่ามันยังคงอยู่หลังการใช้ down และจะหายไปเมื่อใช้ down -v พร้อมทั้งอธิบายกรณีการใช้งาน 2 กรณีที่คุณจำเป็นต้องใช้ --force-recreate

docker compose stop: คอนเทนเนอร์ยังคงอยู่

stop จะส่งสัญญาณ SIGTERM ไปยังกระบวนการหลักในแต่ละคอนเทนเนอร์ จากนั้นจะรอและส่งสัญญาณ SIGKILL หากกระบวนการดังกล่าวยังคงทำงานอยู่ ระยะเวลารอคอยเริ่มต้นคือ 10 วินาที และคุณสามารถใช้ -t เพื่อปรับเปลี่ยนค่านี้ได้ โดยจะไม่มีการลบข้อมูลใดๆ คอนเทนเนอร์จะยังคงรักษา ID, เลเยอร์ที่เขียนได้ (writable layer), การจอง IP และบันทึกการทำงาน (logs) ไว้เหมือนเดิม

docker compose stop
docker compose ps -a

docker compose ps จะแสดงเฉพาะคอนเทนเนอร์ที่กำลังทำงานอยู่เท่านั้น ดังนั้นหลังจากใช้ stop คุณจะเห็นตารางว่างเปล่า ซึ่งทำให้เข้าใจผิดว่าคอนเทนเนอร์ถูกลบไปแล้ว การใช้ ps -a จะแสดงรวมถึงคอนเทนเนอร์ที่หยุดทำงานแล้วด้วย ซึ่งคุณจะเห็นสถานะ Exited (0) ปรากฏอยู่ข้างแต่ละเซอร์วิส คุณสามารถเรียกคอนเทนเนอร์เหล่านั้นกลับมาทำงานได้ด้วย docker compose start ซึ่งจะเป็นการนำคอนเทนเนอร์เดิมกลับมาใช้งานใหม่

เนื่องจากคอนเทนเนอร์ยังคงมีอยู่ ข้อมูลใดๆ ที่เขียนไว้ภายในคอนเทนเนอร์นอกเหนือจากส่วนที่เป็น volume จะยังคงอยู่ครบถ้วน ซึ่งรวมถึงแพ็กเกจที่คุณติดตั้งด้วยตนเองผ่าน docker compose exec และไฟล์คอนฟิกูเรชันที่คุณแก้ไขไว้ภายในคอนเทนเนอร์ นี่คือเหตุผลในทางปฏิบัติที่คุณควรเลือกใช้ stop ในระหว่างการดีบั๊ก เนื่องจากคุณสามารถรีสตาร์ทเพื่อกลับเข้าสู่สถานะเดิมได้

docker compose down: การลบคอนเทนเนอร์และเครือข่าย

down จะหยุดการทำงานของคอนเทนเนอร์และลบทิ้ง รวมถึงลบเครือข่ายเริ่มต้นที่ Compose สร้างขึ้นสำหรับโปรเจกต์นั้น เอกสารประกอบของ Docker อธิบายว่าคำสั่งนี้ทำหน้าที่หยุดและลบคอนเทนเนอร์ เครือข่าย วอลุ่ม และอิมเมจที่สร้างโดย up อย่างไรก็ตาม ส่วนของวอลุ่มและอิมเมจจะถูกลบก็ต่อเมื่อคุณระบุคำสั่ง -v และ --rmi เท่านั้น

docker compose down
docker compose ps -a
docker network ls

หลังจากรัน down แล้ว ps -a จะไม่แสดงผลลัพธ์ใดๆ สำหรับโปรเจกต์นี้ และเครือข่าย <project>_default จะถูกลบออกไป ชื่อของโปรเจกต์จะถูกกำหนดตามชื่อไดเรกทอรี เว้นแต่คุณจะตั้งค่า name: ไว้ในไฟล์ Compose หรือส่งค่าผ่าน -p การเปลี่ยนแปลงใดๆ ที่คุณทำไว้ภายในเลเยอร์ที่เขียนได้ (writable layer) ของคอนเทนเนอร์จะไม่สามารถกู้คืนได้ ดังนั้นให้ถือว่า down เป็นคำสั่งที่ทิ้งคอนเทนเนอร์ไป แต่ยังคงรักษาข้อมูลที่คุณเก็บไว้ในวอลุ่มเอาไว้

หากรันคำสั่งในไดเรกทอรีที่ไม่ถูกต้อง คุณจะได้รับข้อผิดพลาด no configuration file provided: not found เนื่องจาก Compose ไม่ทราบว่าคุณหมายถึงโปรเจกต์ใด จึงปฏิเสธการทำงาน ให้ใช้ docker compose -f /srv/myapp/compose.yaml down ในกรณีที่คุณไม่ได้อยู่ในโฟลเดอร์ของโปรเจกต์นั้น

docker compose down จะลบ volume ของฉันหรือไม่?

ไม่ลบ Named volume ที่ประกาศไว้ภายใต้คีย์ระดับบนสุด volumes จะยังคงอยู่หลังจากใช้คำสั่ง down และจะยังคงอยู่แม้คอนเทนเนอร์ที่เชื่อมต่ออยู่จะถูกลบไปแล้ว นี่เป็นข้อกังวลที่พบบ่อยที่สุดเกี่ยวกับคำสั่งนี้ และคำตอบนี้ยังคงใช้ได้เหมือนเดิมใน Compose v2

ตั้งค่าสแต็กเพื่อทดสอบ ใส่ข้อมูลนี้ลงใน compose.yaml ในไดเรกทอรีว่างที่ชื่อ voltest

services:
  db:
    image: postgres:16.4
    restart: unless-stopped
    environment:
      POSTGRES_PASSWORD: example
    volumes:
      - pgdata:/var/lib/postgresql/data

volumes:
  pgdata:

เริ่มการทำงานและเขียนแถวข้อมูลที่คุณจะจำได้ในภายหลัง

docker compose up -d
sleep 10
docker compose exec -T db psql -U postgres -c "create table marker (note text);"
docker compose exec -T db psql -U postgres -c "insert into marker values ('survived');"

ตอนนี้ให้ทำลายคอนเทนเนอร์และตรวจสอบ volume

docker compose down
docker volume ls

ผลลัพธ์ยังคงแสดงรายการ voltest_pgdata คอนเทนเนอร์ถูกลบไปแล้วแต่ข้อมูลยังคงอยู่ นำสแต็กกลับมาใช้งานอีกครั้งและอ่านแถวข้อมูลนั้น

docker compose up -d
sleep 10
docker compose exec -T db psql -U postgres -c "select * from marker;"

คุณจะได้รับหนึ่งแถวที่มีข้อมูล survived คอนเทนเนอร์ใหม่เป็นคอนเทนเนอร์คนละตัวที่มี ID ต่างกัน แต่เชื่อมต่อกับ volume เดิม หากคุณต้องการภาพรวมที่กว้างขึ้น คู่มือพื้นฐานของ Compose จะครอบคลุมเรื่อง named volumes เทียบกับ bind mounts และตำแหน่งที่จัดเก็บข้อมูลแต่ละประเภทบนโฮสต์จริง ๆ

คำสั่ง down -v ทำลายสิ่งใดบ้าง

-v (รูปแบบเต็มคือ --volumes) จะลบโวลุ่มที่มีการระบุชื่อไว้ในส่วน volumes ของไฟล์ Compose รวมถึงโวลุ่มแบบไม่ระบุชื่อที่เชื่อมต่ออยู่กับคอนเทนเนอร์ ให้รันคำสั่งนี้กับสแต็กเดิม

docker compose down -v
docker volume ls

voltest_pgdata จะไม่ปรากฏในรายการอีกต่อไป หากเริ่มการทำงานของสแต็กใหม่อีกครั้ง Postgres entrypoint จะพบว่าไดเรกทอรีข้อมูลว่างเปล่า จึงทำการเริ่มต้นคลัสเตอร์ใหม่ขึ้นมา บันทึกของคอนเทนเนอร์จะระบุเรื่องนี้ไว้อย่างชัดเจน

The files belonging to this database system will be owned by user "postgres".
PostgreSQL init process complete; ready for start up.

การเห็นข้อความดังกล่าวบนสแต็กที่ทำงานมานานหลายเดือนหมายความว่าโวลุ่มนั้นถูกลบไปแล้ว ตาราง marker ของคุณจะหายไป และวิธีเดียวที่จะกู้คืนได้คือการใช้ข้อมูลสำรอง

พื้นที่จัดเก็บข้อมูลบางส่วนจะไม่ถูกลบโดย -v โดย bind mount คือพาธบนโฮสต์ ดังนั้น Docker จะทำเพียงแค่ยกเลิกการเมานต์ (unmount) และไฟล์ของคุณจะยังคงอยู่ที่เดิม โวลุ่มที่ทำเครื่องหมายว่า external: true จะถูกประกาศว่าขึ้นตรงกับสิ่งอื่นที่อยู่นอกโปรเจกต์นี้ และ Compose จะไม่ลบโวลุ่มดังกล่าวออก โวลุ่มที่มีการระบุชื่อซึ่งคุณลบออกจากไฟล์ Compose ก่อนที่จะรัน down -v จะไม่มีการประกาศไว้อีกต่อไป ดังนั้น Compose จึงไม่ทราบว่าต้องลบโวลุ่มนั้นทิ้ง และมันจะถูกทิ้งไว้เป็นโวลุ่มกำพร้าสำหรับ docker volume prune

กรณีสุดท้ายนี้มักเกิดขึ้นกับผู้ใช้งานระหว่างการปรับโครงสร้าง (refactor) หากคุณลบเซอร์วิสและโวลุ่มออกจากไฟล์ แล้วรัน down -v โวลุ่มนั้นจะยังคงอยู่เพราะไฟล์ไม่ได้อ้างถึงมันอีกต่อไป ให้รัน down -v ก่อนที่คุณจะแก้ไขไฟล์ ไม่ใช่หลังจากนั้น

เมื่อใดที่คุณจำเป็นต้องใช้ --force-recreate

docker compose up -d ไม่ได้สร้างสภาพแวดล้อมใหม่ทุกครั้งที่ทำงาน Compose จะจัดเก็บค่าแฮชของการกำหนดค่าที่แก้ไขแล้วของแต่ละเซอร์วิสไว้บนคอนเทนเนอร์ในรูปแบบเลเบล หากค่าแฮชตรงกันและ ID ของอิมเมจตรงกัน คอนเทนเนอร์จะถูกปล่อยไว้ตามเดิมและคุณจะได้รับ Container voltest-db-1 Running แทนที่จะเป็น Recreated ซึ่งเป็นพฤติกรรมที่คุณต้องการเกือบทุกครั้ง เพราะทำให้การรัน up -d ซ้ำๆ มีความปลอดภัย

นี่คือเหตุผลว่าทำไมการแก้ไขบางอย่างจึงดูเหมือนไม่มีผลอะไร Compose จะแฮชคำจำกัดความของเซอร์วิสที่แก้ไขแล้ว ไม่ใช่เนื้อหาของไฟล์ที่คำจำกัดความนั้นอ้างถึง ไฟล์คอนฟิกที่ถูกเมาท์เข้าไปในคอนเทนเนอร์และถูกอ่านเพียงครั้งเดียวตอนเริ่มต้นระบบ จะไม่กระตุ้นให้เกิดการสร้างใหม่เมื่อคุณแก้ไขไฟล์นั้น เนื่องจากพาธที่เมาท์ไม่ได้เปลี่ยนแปลง เซอร์วิสจะยังคงทำงานต่อไปด้วยค่าที่อ่านได้ตอนบูตระบบ

docker compose up -d --force-recreate

คำสั่งนี้จะหยุดและลบคอนเทนเนอร์แต่ละตัวออก แล้วสร้างคอนเทนเนอร์ใหม่จากคำจำกัดความเดิม ให้ใช้คำสั่งนี้หลังจากแก้ไขไฟล์คอนฟิกที่เมาท์ไว้ หรือเมื่อคอนเทนเนอร์อยู่ในสถานะที่คุณไม่สามารถอธิบายได้ วอลุ่มจะไม่ได้รับผลกระทบ ดังนั้นฐานข้อมูลจะยังคงอยู่หลังจากการบังคับสร้างใหม่ หากต้องการดึงอิมเมจเวอร์ชันใหม่ที่ใช้แท็กเดิม คุณจำเป็นต้องใช้คำสั่งดึงอิมเมจควบคู่ไปด้วย

docker compose pull
docker compose up -d

pull จะดึง ID ของอิมเมจใหม่มา และ up -d จะตรวจพบว่า ID ของอิมเมจแตกต่างจากคอนเทนเนอร์ที่กำลังทำงานอยู่ จึงทำการสร้างคอนเทนเนอร์ใหม่โดยอัตโนมัติ การเพิ่ม --force-recreate โดยไม่มี pull จะทำให้คุณได้คอนเทนเนอร์ใหม่ที่ใช้อิมเมจเดิมตัวเก่า นี่คือเหตุผลว่าทำไมคำบ่นที่ว่า "ฉันบังคับสร้างใหม่แล้วแต่ยังเป็นเวอร์ชันเก่าอยู่" จึงเป็นปัญหาที่พบได้บ่อย

docker compose restart ไม่ได้ทำสิ่งเหล่านี้เลย มันเพียงแค่รีสตาร์ทคอนเทนเนอร์ที่มีอยู่เดิมและไม่ได้อ่านไฟล์ Compose ใหม่เลย ดังนั้นการเปลี่ยนแปลงตัวแปรสภาพแวดล้อมหรือการแมปพอร์ตจะไม่ถูกนำไปใช้ หากคุณแก้ไขไฟล์ ให้ใช้ up -d แทน

แนวคิดที่ควรยึดถือ

คอนเทนเนอร์เป็นสิ่งที่ทดแทนกันได้ คอนเทนเนอร์ประกอบด้วยโพรเซสและเลเยอร์ที่เขียนทับได้แบบบาง ซึ่ง Compose สามารถสร้างคอนเทนเนอร์ที่เหมือนกันขึ้นมาใหม่จากไฟล์ได้ในเวลาประมาณ 1 วินาที ส่วนโวลุ่ม (Volumes) เป็นสิ่งที่ทดแทนไม่ได้ เนื่องจากเป็นที่เก็บสำเนาสถานะเพียงชุดเดียวที่ไม่มีไฟล์ใดในที่เก็บข้อมูล (repository) ของคุณสามารถสร้างขึ้นมาใหม่ได้

คำสั่งทุกคำสั่งของ Compose สอดคล้องกับการแบ่งแยกนี้ stop และ start จะคงคอนเทนเนอร์ไว้ down และ up จะแทนที่คอนเทนเนอร์แต่ยังคงโวลุ่มไว้ down -v เป็นคำสั่งปกติเพียงคำสั่งเดียวที่ลบสถานะทิ้ง ซึ่งเป็นเหตุผลว่าทำไมจึงต้องมีแฟล็กระบุไว้อย่างชัดเจน ก่อนที่คุณจะพิมพ์คำสั่งนี้กับระบบงานจริง ให้ตรวจสอบให้แน่ใจว่าคุณมีข้อมูลสำรองที่คุณเคยทดสอบกู้คืนมาแล้วอย่างน้อยหนึ่งครั้ง

ตรรกะเดียวกันนี้ใช้กับความลับ (secrets) รหัสผ่านที่ตั้งค่าผ่าน POSTGRES_PASSWORD จะถูกอ่านเฉพาะในครั้งแรกที่ฐานข้อมูลเริ่มต้นทำงานเท่านั้น ดังนั้นการเปลี่ยนรหัสผ่านในไฟล์สภาพแวดล้อมของคุณแล้วรัน up -d จะทำให้เกิด password authentication failed for user "postgres" คอนเทนเนอร์จะเป็นชุดใหม่แต่โวลุ่มยังเป็นชุดเดิม และโวลุ่มเดิมนั้นยังคงเก็บรหัสผ่านเก่าเอาไว้ วิธีที่ Compose จัดการกับไฟล์ env และความลับ อธิบายว่าเลเยอร์ใดจะมีผลเหนือกว่าเมื่อมีการตั้งค่าตัวแปรเดียวกันซ้ำสองครั้ง

รูปแบบความล้มเหลวและข้อความที่คุณจะพบ

no configuration file provided: not found หมายความว่า Compose กำลังทำงานอยู่ในไดเรกทอรีที่ไม่มี compose.yaml และไม่มี docker-compose.yml ให้ส่งผ่าน -f พร้อมระบุพาธแบบเต็ม

network voltest_default has active endpoints บน down หมายความว่ามีคอนเทนเนอร์ภายนอกโปรเจกต์นี้เชื่อมต่ออยู่กับเครือข่ายของโปรเจกต์ ซึ่งมักเป็นคอนเทนเนอร์ที่ถูกสั่งเริ่มทำงานด้วยตนเองผ่าน docker run --network ให้ลบคอนเทนเนอร์ดังกล่าวออก แล้วจึงรัน down อีกครั้ง

Found orphan containers ([voltest-old-1]) for this project จะปรากฏขึ้นหลังจากที่คุณเปลี่ยนชื่อหรือลบบริการ คอนเทนเนอร์เดิมยังคงมีป้ายกำกับโปรเจกต์ติดอยู่ docker compose down --remove-orphans จะล้างป้ายกำกับเหล่านี้ออก ซึ่งสามารถรันได้อย่างปลอดภัยบนสแต็กที่ทำงานปกติ

Error response from daemon: remove voltest_pgdata: volume is in use บนการสั่ง docker volume rm ด้วยตนเอง หมายความว่ายังมีคอนเทนเนอร์ที่อ้างอิงถึงวอลุ่มนั้นอยู่ รวมถึงคอนเทนเนอร์ที่หยุดทำงานไปแล้ว ให้รัน docker compose down ก่อน จากนั้นจึงลบวอลุ่ม หรือใช้เพียง down -v สำหรับโปรเจกต์ขนาดใหญ่ สแต็ก Compose แบบหลายบริการ จะแสดงให้เห็นว่าโปรเจกต์หนึ่งสามารถสะสมวอลุ่มได้มากเพียงใด

FAQ

คำสั่ง docker compose down จะลบฐานข้อมูลของฉันหรือไม่

จะไม่ถูกลบหากฐานข้อมูลอยู่ใน named volume หรือ bind mount คำสั่ง down จะลบเฉพาะคอนเทนเนอร์และเครือข่ายของโปรเจกต์ออกไป ส่วน volume จะยังคงอยู่บนดิสก์พร้อมข้อมูลเดิม การรัน docker compose up -d ในครั้งถัดไปจะเชื่อมต่อคอนเทนเนอร์ใหม่เข้ากับ volume เดิมและข้อมูลจะยังคงอยู่ครบถ้วน มีเพียงคำสั่ง docker compose down -v เท่านั้นที่จะลบ named volume ออก และจะลบเฉพาะ volume ที่ประกาศไว้ในส่วน volumes ของไฟล์ Compose เท่านั้น

ความแตกต่างระหว่าง stop และ down สำหรับคอนเทนเนอร์ที่ฉันต้องการใช้งานต่อคืออะไร

คำสั่ง stop จะเก็บคอนเทนเนอร์ไว้ ดังนั้นการใช้ docker compose start จะทำให้คุณกลับไปใช้งานคอนเทนเนอร์เดิมที่มี writable layer เดิมได้ ทุกสิ่งที่ติดตั้งหรือแก้ไขภายในคอนเทนเนอร์ด้วยตนเองจะยังคงอยู่ ส่วนคำสั่ง down จะลบคอนเทนเนอร์ทิ้ง ดังนั้นการใช้ up -d ในครั้งถัดไปจะเป็นการสร้างคอนเทนเนอร์ใหม่จาก image และการเปลี่ยนแปลงที่ทำไว้ด้วยตนเองจะสูญหายไป ในระหว่างการดีบั๊กควรใช้ stop

ฉันจะลบทุกสิ่งที่โปรเจกต์ Compose สร้างขึ้นมาได้อย่างไร

คำสั่ง docker compose down -v --rmi all --remove-orphans จะลบคอนเทนเนอร์, เครือข่ายของโปรเจกต์, named volume ที่ประกาศไว้ในไฟล์, image ที่บริการต่างๆ ใช้งาน และคอนเทนเนอร์ใดๆ ที่ยังมีป้ายกำกับชื่อโปรเจกต์อยู่ คำสั่งนี้จะไม่ส่งผลต่อ bind mount หรือ volume ที่ระบุว่าเป็น external: true ให้ตรวจสอบสิ่งที่จะสูญหายด้วยคำสั่ง docker volume ls ก่อนดำเนินการจริง

ทำไมคอนเทนเนอร์ของฉันถึงไม่สนใจการเปลี่ยนแปลงที่ฉันทำกับไฟล์ config ที่ mount ไว้

Compose จะตัดสินใจว่าจะสร้างคอนเทนเนอร์ใหม่หรือไม่โดยการเปรียบเทียบค่าแฮชของนิยามบริการที่ประมวลผลแล้ว ซึ่งค่าแฮชดังกล่าวไม่ได้รวมเนื้อหาของไฟล์ที่ mount ไว้ เนื่องจากพาธไม่ได้เปลี่ยนแปลง Compose จึงปล่อยให้คอนเทนเนอร์ทำงานต่อไปด้วยค่าที่อ่านได้ตั้งแต่ตอนเริ่มต้น ให้รันคำสั่ง docker compose up -d --force-recreate เพื่อสร้างคอนเทนเนอร์ใหม่ที่จะอ่านไฟล์ดังกล่าวอีกครั้ง

ทำไม POSTGRES_PASSWORD ใหม่ของฉันถึงไม่ทำงานหลังจากที่เปลี่ยนค่าแล้ว

image ของ Postgres จะอ่านค่า POSTGRES_PASSWORD เฉพาะตอนเริ่มต้นสร้างไดเรกทอรีข้อมูลที่ว่างเปล่าเท่านั้น เนื่องจาก volume ของคุณมีคลัสเตอร์ที่เริ่มต้นไว้แล้ว ตัวแปรดังกล่าวจึงถูกละเลยและรหัสผ่านเดิมยังคงมีผลอยู่ คุณจะเห็นข้อความ password authentication failed for user "postgres" ให้เปลี่ยนรหัสผ่านด้วยคำสั่ง ALTER USER ภายในฐานข้อมูลที่กำลังทำงานอยู่ หรือยอมรับการสูญเสียข้อมูลและเริ่มต้นใหม่ด้วยคำสั่ง docker compose down -v