execute_in_container.sh 3.57 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
#!/bin/bash

name="$USER"_work
source="/media/$USER/docker"
it_flag=
d_flag=
run=
exec=
ports=()
ports_arg=()
re='^[0-9]+$'

usage()
{
    echo "Help:"
    echo "-n, --name - name of a container. Default is" $USER"_work."
    echo "-i, --interactive - whether to start the command in interactive mode."
    echo "-d, --detach - whether to detach shell from the command."
    echo "-r, --run - whether to run container if it is not running."
    echo "-e, --exec - whether to execute command if the container is already running."
    echo "-h, --help - show this message."
    echo "-p, --port - choose a port to forward from the container. "
    echo "             For example, if you specify port as a number, e.g. 8888 (standard Jupyter port), container port 8888 will be forwarded to host port 8888. "
    echo "             Otherwise, you can specify port as <host port>:<container port> (i.e. 8880:80) if you want to connect it to a different host port."
    echo ""
    echo "Note: if neither -r nor -e are specified, the default mode is to allow both."
}

if [ ! -d "$source" ]; then
    source="/media/students/$USER/docker"
fi

while [ "$1" != "" ]; do
    case $1 in
        -n | --name )               shift
                                    name="$1"
                                    ;;
        -p | --port )               shift
                                    ports+=( "$1" )
                                    ;;
        -i | --interactive )        it_flag="-it"
                                    ;;
        -d | --detach )             d_flag="-d"
                                    ;;
        -r | --run )                run=1
                                    ;;
        -e | --exec )               exec=1
                                    ;;
        -h | --help )               usage
                                    exit
                                    ;;
        * )                         break
    esac
    shift
done

if [ "$run" != "1" ] && [ "$exec" != "1" ]; then
    run="1"
    exec="1"
fi


for port in ${ports[@]}; do
    if [[ $port =~ $re ]]; then
        for i in {1..10}; do
            nc -z 127.0.0.1 $port
            if [ $? == 1 ]; then
                echo "Port $port is available"
                break
            else
                echo "Port $port is not available"
                port=$((port+1))
                echo "Trying port $port..."
            fi
        done
        ports_arg+=( "-p" "$port:$port" )
    else
        ports_arg+=( "-p" $port )
    fi
done

CONTAINER_PATH=/$USER/env/work/bin:/opt/conda/bin:/usr/local/nvidia/bin:/usr/local/cuda/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
JUPYTER_CONFIG_DIR=/$USER/.jupyter/.config
JUPYTER_DATA_DIR=/$USER/.jupyter
JUPYTER_RUNTIME_DIR=/$USER/.jupyter/runtime

if [ ! "$(docker ps -q -f name=$name)" ]; then
    if [ "$run" = "1" ]; then
        if [ "$(docker ps -aq -f status=exited -f name=$name)" ]; then
            echo "Removing stopped container $name"
            docker rm $name
        fi
        echo "Running container $name with command \"$@\""
        docker run $it_flag $d_flag --name $name --gpus all "${ports_arg[@]}" \
          --env USER --env PATH=$CONTAINER_PATH \
          --env JUPYTER_CONFIG_DIR=$JUPYTER_CONFIG_DIR \
          --env JUPYTER_DATA_DIR=$JUPYTER_DATA_DIR \
          --env JUPYTER_RUNTIME_DIR=$JUPYTER_RUNTIME_DIR \
          --mount type=bind,source=$source,target=/$USER \
          cuda_conda:latest "$@"
    fi
else
    if [ "$exec" = "1" ]; then
        echo "Executing \"$@\" in the container $name"
        docker exec $it_flag $d_flag $name "$@"
    fi
fi