├── Dockerfile ├── README.md ├── entry.sh ├── menu ├── supervisord.conf └── xrdp.ini /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM alpine:edge 2 | 3 | RUN echo "http://dl-cdn.alpinelinux.org/alpine/edge/testing" >> /etc/apk/repositories 4 | RUN apk update 5 | RUN apk add --no-cache xvfb x11vnc fluxbox supervisor xterm bash chromium firefox xrdp wqy-zenhei novnc websockify 6 | 7 | RUN ln -s /usr/share/novnc/vnc_lite.html /usr/share/novnc/index.html 8 | 9 | ADD supervisord.conf /etc/supervisord.conf 10 | ADD xrdp.ini /etc/xrdp/xrdp.ini 11 | ADD menu /root/.fluxbox/menu 12 | ADD entry.sh /entry.sh 13 | 14 | RUN chmod +x /entry.sh 15 | 16 | ENV DISPLAY :0 17 | ENV RESOLUTION=1024x768 18 | 19 | EXPOSE 5901 6901 20 | 21 | ENTRYPOINT ["/bin/bash", "-c", "/entry.sh"] 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Alpine docker container image with "headless" VNC/RDP environments 2 | 3 | Installed with the following components: 4 | 5 | * Desktop environment [**Fluxbox**](http://fluxbox.org) 6 | * xrdp server (default RDP port `3389`) 7 | * vnc server (default VNC port `5901`) 8 | * [**noVNC**](https://github.com/novnc/noVNC) - HTML5 VNC client (default http port `6901`) 9 | * Browsers: 10 | * Chromium 11 | * Firefox 12 | 13 | 14 | ## Current provided OS & UI sessions: 15 | 16 | * `soff/tiny-remote-desktop`: __Alpine with `Fluxbox` UI session__ 17 | 18 | 19 | ## Usage 20 | 21 | - Run command with mapping to local port `5901` (vnc protocol) and `6901` (vnc web access): 22 | 23 | docker run -d -p 5901:5901 -p 6901:6901 soff/tiny-remote-desktop 24 | 25 | - Run command with mapping to local port `3389` (rdp protocol): 26 | 27 | docker run -d -p 3389:3389 soff/tiny-remote-desktop 28 | 29 | - Run command with mapping to local port `5901` (vnc protocol) and `6901` (vnc web access) with access password: 30 | 31 | docker run -d -p 5901:5901 -p 6901:6901 -e VNC_PASSWORD="vncpassword" soff/tiny-remote-desktop 32 | 33 | - Run command with mapping to local port `5901` (vnc protocol) and `6901` (vnc web access) with specific resolution: 34 | 35 | docker run -d -p 5901:5901 -p 6901:6901 -e RESOLUTION=1600x1200 soff/tiny-remote-desktop 36 | 37 | ## Hints 38 | 39 | ### 1) No start menu? 40 | Just right click on desktop, the start menu will pop up. 41 | -------------------------------------------------------------------------------- /entry.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | if [ "$VNC_PASSWORD" ]; then 4 | sed -i "s/^\(command.*x11vnc.*\)$/\1 -passwd '$VNC_PASSWORD'/" /etc/supervisord.conf 5 | fi 6 | 7 | /usr/bin/supervisord -------------------------------------------------------------------------------- /menu: -------------------------------------------------------------------------------- 1 | # Generated by fluxbox-generate_menu 2 | # 3 | # If you read this it means you want to edit this file manually, so here 4 | # are some useful tips: 5 | # 6 | # - You can add your own menu-entries to ~/.fluxbox/usermenu 7 | # 8 | # - If you miss apps please let me know and I will add them for the next 9 | # release. 10 | # 11 | # - The -r option prevents removing of empty menu entries and lines which 12 | # makes things much more readable. 13 | # 14 | # - To prevent any other app from overwriting your menu 15 | # you can change the menu name in ~/.fluxbox/init to: 16 | # session.menuFile: ~/.fluxbox/my-menu 17 | [begin] (Fluxbox-1.3.7) 18 | [encoding] {UTF-8} 19 | [exec] (Xterm) {xterm} 20 | [exec] (Chromium) {chromium-browser --no-sandbox} 21 | [exec] (Firefox) {firefox} 22 | [submenu] (Editors) 23 | [exec] (vi) {xterm -e vi} 24 | [end] 25 | [submenu] (System Tools) 26 | [exec] (top) {xterm -e top} 27 | [end] 28 | [submenu] (Fluxbox menu) 29 | [config] (Configure) 30 | [submenu] (System Styles) {Choose a style...} 31 | [stylesdir] (/usr/share/fluxbox/styles) 32 | [end] 33 | [submenu] (User Styles) {Choose a style...} 34 | [stylesdir] (~/.fluxbox/styles) 35 | [end] 36 | [workspaces] (Workspace List) 37 | [commanddialog] (Fluxbox Command) 38 | [reconfig] (Reload config) 39 | [restart] (Restart) 40 | [exec] (About) {(fluxbox -v; fluxbox -info | sed 1d) | xmessage -file - -center} 41 | [separator] 42 | [exit] (Exit) 43 | [end] 44 | [endencoding] 45 | [end] 46 | -------------------------------------------------------------------------------- /supervisord.conf: -------------------------------------------------------------------------------- 1 | [supervisord] 2 | nodaemon=true 3 | 4 | [program:X11] 5 | command=/usr/bin/Xvfb :0 -screen 0 %(ENV_RESOLUTION)sx24 6 | autorestart=true 7 | 8 | [program:x11vnc] 9 | command=/usr/bin/x11vnc -xkb -noxrecord -noxfixes -noxdamage -display :0 -nopw -wait 5 -shared -permitfiletransfer -tightfilexfer -rfbport 5901 10 | autorestart=true 11 | 12 | [program:novnc] 13 | command=/usr/bin/novnc_server --vnc localhost:5901 --listen 6901 14 | autorestart=true 15 | 16 | [program:fluxbox] 17 | command=/usr/bin/fluxbox 18 | autorestart=true 19 | 20 | [program:xterm] 21 | command=/usr/bin/xterm 22 | autorestart=false 23 | startretries = 1 24 | 25 | [program:xrdp] 26 | command=/usr/sbin/xrdp 27 | autorestart=true 28 | startretries = 1 29 | 30 | [program:chromium] 31 | command=/usr/bin/chromium-browser --no-sandbox 32 | autorestart=false 33 | startretries = 1 34 | -------------------------------------------------------------------------------- /xrdp.ini: -------------------------------------------------------------------------------- 1 | [Globals] 2 | ; xrdp.ini file version number 3 | ini_version=1 4 | 5 | ; fork a new process for each incoming connection 6 | fork=true 7 | 8 | ; ports to listen on, number alone means listen on all interfaces 9 | ; 0.0.0.0 or :: if ipv6 is configured 10 | ; space between multiple occurrences 11 | ; 12 | ; Examples: 13 | ; port=3389 14 | ; port=unix://./tmp/xrdp.socket 15 | ; port=tcp://.:3389 127.0.0.1:3389 16 | ; port=tcp://:3389 *:3389 17 | ; port=tcp://:3389 192.168.1.1:3389 18 | ; port=tcp6://.:3389 ::1:3389 19 | ; port=tcp6://:3389 *:3389 20 | ; port=tcp6://{}:3389 {FC00:0:0:0:0:0:0:1}:3389 21 | ; port=vsock://: 22 | port=3389 23 | 24 | ; 'port' above should be connected to with vsock instead of tcp 25 | ; use this only with number alone in port above 26 | ; prefer use vsock://: above 27 | use_vsock=false 28 | 29 | ; regulate if the listening socket use socket option tcp_nodelay 30 | ; no buffering will be performed in the TCP stack 31 | tcp_nodelay=true 32 | 33 | ; regulate if the listening socket use socket option keepalive 34 | ; if the network connection disappear without close messages the connection will be closed 35 | tcp_keepalive=true 36 | 37 | ; set tcp send/recv buffer (for experts) 38 | #tcp_send_buffer_bytes=32768 39 | #tcp_recv_buffer_bytes=32768 40 | 41 | ; security layer can be 'tls', 'rdp' or 'negotiate' 42 | ; for client compatible layer 43 | security_layer=negotiate 44 | 45 | ; minimum security level allowed for client for classic RDP encryption 46 | ; use tls_ciphers to configure TLS encryption 47 | ; can be 'none', 'low', 'medium', 'high', 'fips' 48 | crypt_level=high 49 | 50 | ; X.509 certificate and private key 51 | ; openssl req -x509 -newkey rsa:2048 -nodes -keyout key.pem -out cert.pem -days 365 52 | certificate= 53 | key_file= 54 | 55 | ; set SSL protocols 56 | ; can be comma separated list of 'SSLv3', 'TLSv1', 'TLSv1.1', 'TLSv1.2', 'TLSv1.3' 57 | ssl_protocols=TLSv1.2, TLSv1.3 58 | ; set TLS cipher suites 59 | #tls_ciphers=HIGH 60 | 61 | ; Section name to use for automatic login if the client sends username 62 | ; and password. If empty, the domain name sent by the client is used. 63 | ; If empty and no domain name is given, the first suitable section in 64 | ; this file will be used. 65 | autorun=Xvnc 66 | 67 | allow_channels=true 68 | allow_multimon=true 69 | bitmap_cache=true 70 | bitmap_compression=true 71 | bulk_compression=true 72 | #hidelogwindow=true 73 | max_bpp=32 74 | new_cursors=true 75 | ; fastpath - can be 'input', 'output', 'both', 'none' 76 | use_fastpath=both 77 | ; when true, userid/password *must* be passed on cmd line 78 | #require_credentials=true 79 | ; You can set the PAM error text in a gateway setup (MAX 256 chars) 80 | #pamerrortxt=change your password according to policy at http://url 81 | 82 | ; 83 | ; colors used by windows in RGB format 84 | ; 85 | blue=009cb5 86 | grey=dedede 87 | #black=000000 88 | #dark_grey=808080 89 | #blue=08246b 90 | #dark_blue=08246b 91 | #white=ffffff 92 | #red=ff0000 93 | #green=00ff00 94 | #background=626c72 95 | 96 | ; 97 | ; configure login screen 98 | ; 99 | 100 | ; Login Screen Window Title 101 | #ls_title=My Login Title 102 | 103 | ; top level window background color in RGB format 104 | ls_top_window_bg_color=009cb5 105 | 106 | ; width and height of login screen 107 | ls_width=350 108 | ls_height=430 109 | 110 | ; login screen background color in RGB format 111 | ls_bg_color=dedede 112 | 113 | ; optional background image filename (bmp format). 114 | #ls_background_image= 115 | 116 | ; logo 117 | ; full path to bmp-file or file in shared folder 118 | ls_logo_filename= 119 | ls_logo_x_pos=55 120 | ls_logo_y_pos=50 121 | 122 | ; for positioning labels such as username, password etc 123 | ls_label_x_pos=30 124 | ls_label_width=65 125 | 126 | ; for positioning text and combo boxes next to above labels 127 | ls_input_x_pos=110 128 | ls_input_width=210 129 | 130 | ; y pos for first label and combo box 131 | ls_input_y_pos=220 132 | 133 | ; OK button 134 | ls_btn_ok_x_pos=142 135 | ls_btn_ok_y_pos=370 136 | ls_btn_ok_width=85 137 | ls_btn_ok_height=30 138 | 139 | ; Cancel button 140 | ls_btn_cancel_x_pos=237 141 | ls_btn_cancel_y_pos=370 142 | ls_btn_cancel_width=85 143 | ls_btn_cancel_height=30 144 | 145 | [Logging] 146 | LogFile=xrdp.log 147 | LogLevel=DEBUG 148 | EnableSyslog=true 149 | SyslogLevel=DEBUG 150 | ; LogLevel and SysLogLevel could by any of: core, error, warning, info or debug 151 | 152 | [Channels] 153 | ; Channel names not listed here will be blocked by XRDP. 154 | ; You can block any channel by setting its value to false. 155 | ; IMPORTANT! All channels are not supported in all use 156 | ; cases even if you set all values to true. 157 | ; You can override these settings on each session type 158 | ; These settings are only used if allow_channels=true 159 | rdpdr=true 160 | rdpsnd=true 161 | drdynvc=true 162 | cliprdr=true 163 | rail=true 164 | xrdpvr=true 165 | tcutils=true 166 | 167 | ; for debugging xrdp, in section xrdp1, change port=-1 to this: 168 | #port=/tmp/.xrdp/xrdp_display_10 169 | 170 | ; for debugging xrdp, add following line to section xrdp1 171 | #chansrvport=/tmp/.xrdp/xrdp_chansrv_socket_7210 172 | 173 | 174 | ; 175 | ; Session types 176 | ; 177 | 178 | ; Some session types such as Xorg, X11rdp and Xvnc start a display server. 179 | ; Startup command-line parameters for the display server are configured 180 | ; in sesman.ini. See and configure also sesman.ini. 181 | [Xvnc] 182 | name=Xvnc 183 | lib=libvnc.so 184 | username=root 185 | password= 186 | ip=127.0.0.1 187 | port=5901 188 | #xserverbpp=24 189 | #delay_ms=2000 190 | 191 | ; You can override the common channel settings for each session type 192 | #channel.rdpdr=true 193 | #channel.rdpsnd=true 194 | #channel.drdynvc=true 195 | #channel.cliprdr=true 196 | #channel.rail=true 197 | #channel.xrdpvr=true 198 | --------------------------------------------------------------------------------