qemus / qemu-docker

QEMU in a Docker container.
MIT License
496 stars 59 forks source link

[Question]: How to create a disk snapshot? #578

Closed FengZhongShaoNian closed 3 months ago

FengZhongShaoNian commented 3 months ago

Is your question not already answered in the FAQ?

Is this a general question and not a technical issue?

Question

Is there any way to create a snapshot for my virtual machine so that I can roll back the virtual machine when necessary?

NateChoe1 commented 3 months ago

First, extract your existing disk with the following command:

docker cp qemu:/storage ./storage

If your virtual machine container has a different name or container id, use that instead of qemu.

Then, add the following lines to your docker-compose.yml file.

  volumes:
    ./storage:/storage

Now, restart your container. There should be a file in ./storage called data.img or data.qcow. This contains your disk. Whenever you want to make a snapshot, stop the container, copy this to some safe location, and start the container again. When you want to restore from a snapshot, stop the container, replace data.img with the backup that you made, and start the container.

FengZhongShaoNian commented 3 months ago

First, extract your existing disk with the following command:

docker cp qemu:/storage ./storage

If your virtual machine container has a different name or container id, use that instead of qemu.

Then, add the following lines to your docker-compose.yml file.

  volumes:
    ./storage:/storage

Now, restart your container. There should be a file in ./storage called data.img or data.qcow. This contains your disk. Whenever you want to make a snapshot, stop the container, copy this to some safe location, and start the container again. When you want to restore from a snapshot, stop the container, replace data.img with the backup that you made, and start the container.

Thank you for your response. Is backing up the disk file the only method? It seems like a waste of storage space. Is it not possible to use QEMU's snapshot feature?

FengZhongShaoNian commented 3 months ago

I found a way to create a snapshot:

When creating a container, use the environment variable DISK_FMT=qcow2 to specify the format of the virtual disk.

If at some point you want to create a snapshot of your VM, you can shut down the VM first, and then use the script I wrote:

#!/bin/bash

SCRIPT=$(cat <<EOF
list_snapshots(){
    qemu-img snapshot -l /data/data.qcow2
}

create_snapshot(){
    local snapshot_name=''
    while [[ "\$snapshot_name" == '' ]];do
        read -p "Please enter a snapshot name: " snapshot_name
    done
    qemu-img snapshot -c "\$snapshot_name" /data/data.qcow2
}

revert(){
    local snapshot_name=''
    while [[ "\$snapshot_name" == '' ]];do
        read -p "Please enter a snapshot name: " snapshot_name
    done
    qemu-img snapshot -a "\$snapshot_name" /data/data.qcow2
}

delete_snapshot(){
    local snapshot_name=''
    while [[ "\$snapshot_name" == '' ]];do
        read -p "Please enter a snapshot name: " snapshot_name
    done
    qemu-img snapshot -d "\$snapshot_name" /data/data.qcow2
}

is_exit='n'
while [[ "\$is_exit" != 'y' ]];do
    echo '------------------------------------------'
    echo 'l: lists all snapshots in the given image'
    echo 'c: creates a snapshots'
    echo 'r: revert disk to saved state'
    echo 'd: deletes a snapshot'
    echo 'e: exit'
    echo '------------------------------------------'
    operation=''
    read -p "Please select the operation you need to perform:" operation
    if [[ "\$operation" == 'l' ]];then
        list_snapshots
    elif [[ "\$operation" == 'c' ]];then
        create_snapshot
    elif [[ "\$operation" == 'r' ]];then
        revert
    elif [[ "\$operation" == 'd' ]];then
        delete_snapshot
    elif [[ "\$operation" == 'e' ]];then
        exit 0
    fi
done
EOF
)

podman run -it --rm \
-v ./data:/data \
--entrypoint "" \
qemux/qemu-docker:latest \
bash -c "$SCRIPT"