I've got a program that needs to automatically install & manage some Docker containers on Windows with minimal user input.
It needs to automatically setup Docker to mount arbitrary Windows folders. It needs to do this from a clean install, where the Docker VM cannot be assumed to have been created.
Docker by default will allow almost any folder in C:\Users to mount through to its Boot2Docker image, which in turn makes them available for mounting into Docker images themselves.
I'd like a way to automatically modify the default mount script from outside the VM so that I can use other folders, but "VBoxManage.exe run", copyto, etc. commands don't work on Boot2Docker in any way, unlike other Linux VMs I have.
So, in my quest for a solution, I stumbled upon py-vbox, which lets you easily send keyboard events to the console using the VirtualBox API. It also allows for direct console sessions, but they fail just like VBoxManage.exe does. So, this ended with me sending lots of
echo command >> /c/script.sh
commands over the keyboard in order to setup a script that will mount the extra volumes. Is there a better way?
For anyone who might need it, here's a very simplified version of what goes on. The first two bits are the old .bat files, so that they apply to anyone. First, to create our docker VM:
set PATH=%PATH%;"c:\Program Files (x86)\Git\bin"
docker-machine create --driver virtualbox my-docker-vm
"C:\Program Files\Oracle\VirtualBox\VBoxManage.exe" sharedfolder add "my-docker-vm" --name "c/myfolder" --hostpath "c:\myfolder" --automount
"C:\Program Files\Oracle\VirtualBox\VBoxManage.exe" setextradata "my-docker-vm" VBoxInternal2/SharedFoldersEnableSymlinksCreate/c/myfolder 1
Then, the docker VM must be started...
"C:\Program Files\Oracle\VirtualBox\VBoxManage.exe" startvm --type=headless my-docker-vm
set PATH=%PATH%;"c:\Program Files (x86)\Git\bin"
docker-machine env --shell cmd my-docker-vm > temp.cmd
call temp.cmd
del temp.cmd
Now, a simplified version of the Python script to write a simplified mount script into the VM via the keyboard using py-vbox:
import virtualbox
script = """\n\
echo if [ ! -d /c/myfolder ] > /c/script.sh\n\
echo then >> /c/script.sh\n\
echo mkdir -p /c/myfolder >> /c/script.sh\n\
echo mount -t vboxsf c/myfolder /c/myfolder >> /c/script.sh\n\
echo fi >> /c/script.sh\n\
chmod +x /c/script.sh\n\
/bin/sh /c/script.sh\n\
rm /c/script.sh\n\
"""
my_vm_name = 'my-docker-vm'
def mount_folder():
vbox = virtualbox.VirtualBox()
is_there = False
for vmname in vbox.machines:
if str(vmname) == my_vm_name:
is_there = True
break
if is_there is False:
raise whatever
return
vm = vbox.find_machine(my_vm_name)
session = vm.create_session()
session.console.keyboard.put_keys(script)