How to convert DOT graph to ASCII

The GraphViz DOT is a super-simple language that makes it very easy to create graphs and export them to various graphical formats. However, there are situations where you want to generate an ASCII graph. For example, to embed a flowchart or digraph in source code or documentation. GraphViz provides no exporter that can output an ASCII graph.

Thankfully, I found that this can be achieved using a Perl module called Graph::Easy. It can use GraphViz to understand your DOT file and then convert that to an elegant ASCII graph.

Here is how to use that:

  • We need to install the Graph::Easy module from CPAN. Make sure you have CPANMinus already installed, as described here. We install the Graph module like this:
$ sudo cpanm Graph::Easy
  • The Graph::Easy module installs a graph-easy program which we use to convert DOT graph to ASCII:

$ graph-easy life.dot

Tried with: Perl 5.22 and CPAN 1.61

Advertisements

Docker cheatsheet

  • To view Docker images available on your local computer:
$ docker images
  • By default, only the images that you pulled by name are displayed. To view all images on your local computer, including the unnamed intermediate images that were pulled down to compose the named images that you pulled:
$ docker images -a
  • To view the full repository name, tag name and ID of images, use the --no-trunc option:
$ docker images --no-trunc
  • To view all running containers:
$ docker ps
  • To view all containers, not just the running ones:
$ docker ps -a
  • To view the full container ID, image name and command use the --no-trunc option:
$ docker ps --no-trunc

Tried with: Docker 17.09 and Ubuntu 16.04

How to reload group assignment without logout and login

Problem

I was working in a shell in KDE. I installed Docker as described here. To be able to run Docker commands, my username should be in the docker group, so I added that. Now I need to logout and login out of my desktop environment for my username’s new group assignments to be picked up. Otherwise, running any Docker command throws this error:

$ docker images
Got permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock: Get http://%2Fvar%2Frun%2Fdocker.sock/v1.32/images/json: dial unix /var/run/docker.sock: connect: permission denied

We can see that our user’s new group assignment is not reflected in the shell by running this command:

$ id

You will find that the docker group will not appear in the user’s group assignment, though the user has been already added to it. Creating a new shell or a child shell does not achieve what we want.

The only way to get the new group assignment is to logout and login from the desktop environment. The problem I have so many other GUI applications open in my desktop environment. I cannot afford to logout and login from my desktop environment, especially for a shell command to work!

Solution

So, what we want is a shell environment that is similar to what is presented when you login directly at a virtual terminal. Thankfully, we can do that by using the - option of the su command, like this:

$ su - joe
$ docker images
It works!

Another alternative is to run a command with a specific group or GID:

$ sg docker -c "docker images"

Tried with: Docker 17.09 and Ubuntu 16.04

How to install Docker

One way to install Docker is to add its repository and then install it from it. There are a lot of steps that need to be done for this, as seen here.

Since I do not really update packages so often, I prefer downloading the DEB file and installing it manually.

$ sudo dpkg -i your_docker_file.deb
  • Remember to add your username to the docker group:
$ sudo adduser joe docker
  • You will need to logout and login for the group assignment to take effect. If you find that logout-login to be painful, try this trick.

  • Try Docker and see if it works:

$ docker run hello-world

Tried with: Docker 17.09 and Ubuntu 16.04

How to rename remote branch in Git

Git is known for its confusing and difficult commands. If you want to rename a remote branch, say a branch that is on Github, from the comfort of your shell then you are in luck for one such experience! 🙂

This is the invocation to rename a branch old_branch on a remote named foo_remote to a new branch name new_branch:

$ git push foo_remote foo_remote/old_branch:refs/heads/new_branch :old_branch

If you find yourself renaming remote branches a lot, then it is better to add this as a Git command. To do that, save this piece of shell script code as a file named git-rename-remote-branch:

The file can be named anything as long as it begins with a git- prefix. Make it executable and place it in any directory that is in your PATH.

Now, you can rename a remote branch with a sane command:

$ git rename-remote-branch foo_remote old_branch new_branch

Tried with: Git 2.7.4 and Ubuntu 14.04

NVIDIA Docker no such file error

Problem

NVIDIA Docker makes it easy to use Docker containers across machines with differing NVIDIA graphics drivers. After installing it, I ran a sample NVIDIA Docker command and got this error:

$ nvidia-docker run --rm nvidia/cuda nvidia-smi
docker: Error response from daemon: Post http://%2Frun%2Fdocker%2Fplugins%2Fnvidia-docker.sock/VolumeDriver.Mount: dial unix /run/docker/plugins/nvidia-docker.sock: connect: no such file or direct

Investigating the log files showed this:

$ cat /tmp/nvidia-docker.log 
nvidia-docker-plugin | 2017/10/11 10:10:07 Loading NVIDIA unified memory
nvidia-docker-plugin | 2017/10/11 10:10:07 Loading NVIDIA management library
nvidia-docker-plugin | 2017/10/11 10:10:07 Discovering GPU devices
nvidia-docker-plugin | 2017/10/11 10:10:13 Provisioning volumes at /var/lib/nvidia-docker/volumes
nvidia-docker-plugin | 2017/10/11 10:10:13 Serving plugin API at /run/docker/plugins
nvidia-docker-plugin | 2017/10/11 10:10:13 Serving remote API at localhost:3476
nvidia-docker-plugin | 2017/10/11 10:10:13 Error: listen tcp 127.0.0.1:3476: bind: address already in use

That 3476 port turned out to be owned by no process. So what’s the problem?

Solution

I gave up and restarted Docker and everything worked fine after that (haha!):

$ sudo service docker restart

Tried with: NVIDIA Docker 1.x and Docker 1.11

Docker no pull access error

Problem

A Docker pull command to Docker hub that worked fine for all users failed only for one user. When she tried to pull, it threw up this error:

repository some_org/some_image not found: does not exist or no pull access
The push refers to a repository [docker.io/some_org/some_image]

Docker hub authentication and other details seemed to be in order.

Solution

Turns out this user had run some docker commands before adding the Docker hub authentication. Those early commands had created a ~/.docker directory. Details from this were conflicting with Docker hub authentication that was introduced later. Removing this directory fixed the issue.

Tried with: Docker 1.11 and Ubuntu 14.04

How to convert datetime to and from ISO 8601 string

ISO 8601 is a standardized format for representing date and time that is popular. Python has built-in support to convert to and from this format. But confusingly, those methods are distributed across two different modules!

  • Convert a datetime object to string in ISO 8601 format:
import datetime
datetime_str = some_datetime_obj.isoformat()
  • Convert a ISO 8601 format string to datetime object:
import dateutil.parser
some_datetime_obj = dateutil.parser.parse(datetime_str)