nsinit
provides a handy way to access a shell inside a running container's namespace. This is useful for learning about how containers work, debugging your system without worrying about sshd daemons, and even hot fixes in production all you sad pandas!
:p
Running the docker daemon with the lxc driver allows you to use lxc-attach
to do this. But now that docker deafults to the new native libcontainer driver, nsinit
is probably the best way to go. jpetazzo's blog has a great high level summary.
The new issue is that the libcontainer .json format is under heavy development so you need to keep an nsinit
binary built from the exact release tag from the the docker github repo. The tricky part for me was understanding that golang is designed with certain assumptions about dependencies vs versioning with regards to when you push to master, push to a topic branch, and fork a project.
Long story short, I just modified crosbymichael's Dockerfile for skydock to build nsinit in a container and then copy it out to my Linux host system. Here is the procedure:
Get yourself the docker repo and select the tag that matches the daemon version installed on your host system.
$ cd ~/projects
$ git clone https://github.com/dotcloud/docker.git
$ cd docker
$ git checkout -b v1.0.0 tags/v1.0.0 # create a local branch from the tagged version
Put this Dockerfile in the nsinit directory.
$ cd pkg/libcontainer/nsinit
$ vi Dockerfile
Dockerfile:
FROM crosbymichael/golang
# setup build environment
RUN apt-get update && \
apt-get install -y \
build-essential
# install just the deps
RUN go get -d github.com/dotcloud/docker/pkg/libcontainer/nsinit
# stuff in the specifically tagged code from the current directory
ADD . /go/src/github.com/dotcloud/docker/pkg/libcontainer/nsinit
# build a binary image
RUN cd /go/src/github.com/dotcloud/docker/pkg/libcontainer/nsinit && \
go install . ./...
$ docker build -t ubergarm/nsinit .
$ docker run --name nsinit -d ubergarm/nsinit
$ docker cp nsinit:/go/bin/nsinit ./outdir/
$ docker rm nsinit
$ docker rmi ubergarm/nsinit
Confirm you can run the binary on your host system by checking with ldd ./outdir/nsinit.new
and ./outdir/nsinit.new
.
Do this however you'd like. Something like this should be close enough.
$ sudo chmod 755 ./outdir/nsinit
$ sudo chown root:root ./outdir/nsinit
$ sudo mv ./outdir/nsinit /usr/local/bin/nsinit-1.0.0
$ sudo ln -s /usr/local/bin/nsinit-1.0.0 /usr/local/bin/nsinit
Since it is a pain to manually look up the container hash and find the directory I put together a script:
#!/bin/bash
[[ -n "$1" ]] || { echo "Usage: `basename $0` <partial container ID or name>"; exit 0 ; }
FULL_ID=$(docker inspect --format='{{.Id}}' $1)
# LXC driver method:
# sudo lxc-attach -n $FULL_ID /bin/bash
# libcontainer driver method:
sudo bash -c "cd /var/lib/docker/execdriver/native/$FULL_ID && nsinit exec bash"
Now hop in your favorite running container and have some fun!
Hi
This the error I got when I run docker build -t ubergarm/nsinit .
Step 10 : RUN cd /go/src/github.com/dotcloud/docker/pkg/libcontainer/nsinit && go install . ./...
---> Running in fe1a70e0dbdd
found packages nsinit (create.go) and main (main.go) in .
can't load package: package github.com/dotcloud/docker/pkg/libcontainer/nsinit: found packages nsinit (create.go) and main (main.go) in /go/src/github.com/dotcloud/docker/pkg/libcontainer/nsinit
package github.com/dotcloud/docker/pkg/libcontainer/nsinit: found packages nsinit (create.go) and main (main.go) in /go/src/github.com/dotcloud/docker/pkg/libcontainer/nsinit
Please assist I need nsinit urgently :)