├── README.md ├── dockerfunc ├── rpi-acarsdec ├── Dockerfile ├── Makefile └── acarsdec-3.2.tar.gz ├── rpi-alexa ├── Dockerfile └── creds.py ├── rpi-android-tools ├── Dockerfile ├── insecure_shared_adbkey └── insecure_shared_adbkey.pub ├── rpi-apt-file └── Dockerfile ├── rpi-arduino └── Dockerfile ├── rpi-beacon └── Dockerfile ├── rpi-bladerf-yatebts ├── Dockerfile ├── subscribers.conf └── ybts.conf ├── rpi-bladerf └── Dockerfile ├── rpi-busybox-httpd ├── Dockerfile ├── LICENSE ├── Makefile ├── README.md ├── dockerize-busybox-httpd.sh ├── index.html ├── install-deps.sh ├── pi_armed_with_docker.jpg └── start-webservers.sh ├── rpi-cheese └── Dockerfile ├── rpi-chromium └── Dockerfile ├── rpi-dashing ├── Dockerfile └── dashboard │ ├── .gitignore │ ├── Gemfile │ ├── Gemfile.lock │ ├── README.md │ ├── assets │ ├── fonts │ │ ├── fontawesome-webfont.eot │ │ ├── fontawesome-webfont.svg │ │ ├── fontawesome-webfont.ttf │ │ └── fontawesome-webfont.woff │ ├── images │ │ └── logo.png │ ├── javascripts │ │ ├── application.coffee │ │ ├── d3-3.2.8.js │ │ ├── dashing.gridster.coffee │ │ ├── gridster │ │ │ ├── jquery.gridster.js │ │ │ └── jquery.leanModal.min.js │ │ ├── jquery.knob.js │ │ └── rickshaw-1.4.3.min.js │ └── stylesheets │ │ ├── application.scss │ │ ├── font-awesome.css │ │ └── jquery.gridster.css │ ├── config.ru │ ├── dashboards │ ├── layout.erb │ ├── sample.erb │ └── sampletv.erb │ ├── jobs │ ├── buzzwords.rb │ ├── convergence.rb │ ├── sample.rb │ └── twitter.rb │ ├── public │ ├── 404.html │ └── favicon.ico │ ├── start.sh │ └── widgets │ ├── clock │ ├── clock.coffee │ ├── clock.html │ └── clock.scss │ ├── comments │ ├── comments.coffee │ ├── comments.html │ └── comments.scss │ ├── graph │ ├── graph.coffee │ ├── graph.html │ └── graph.scss │ ├── iframe │ ├── iframe.coffee │ ├── iframe.html │ └── iframe.scss │ ├── image │ ├── image.coffee │ ├── image.html │ └── image.scss │ ├── list │ ├── list.coffee │ ├── list.html │ └── list.scss │ ├── meter │ ├── meter.coffee │ ├── meter.html │ └── meter.scss │ ├── number │ ├── number.coffee │ ├── number.html │ └── number.scss │ └── text │ ├── text.coffee │ ├── text.html │ └── text.scss ├── rpi-dnsmasq ├── Dockerfile └── dnsmasq.conf ├── rpi-dump1090 └── Dockerfile ├── rpi-epiphany └── Dockerfile ├── rpi-errbot ├── Dockerfile ├── config.py ├── requirements.txt └── run.sh ├── rpi-festival └── Dockerfile ├── rpi-flite └── Dockerfile ├── rpi-freqshow └── Dockerfile ├── rpi-glances └── Dockerfile ├── rpi-gnuradio └── Dockerfile ├── rpi-gpio-gmail ├── Dockerfile └── gpio_gmail.py ├── rpi-gpio-python └── Dockerfile ├── rpi-gtalk-robot └── Dockerfile ├── rpi-guvcview └── Dockerfile ├── rpi-hostapd ├── Dockerfile ├── dnsmasq.conf └── hostapd.conf ├── rpi-iceweasel └── Dockerfile ├── rpi-kalibrate └── Dockerfile ├── rpi-kitematic └── Dockerfile ├── rpi-kivy-infoscreen └── Dockerfile ├── rpi-kivy └── Dockerfile ├── rpi-libreoffice └── Dockerfile ├── rpi-lynx └── Dockerfile ├── rpi-midori └── Dockerfile ├── rpi-minecraft └── Dockerfile ├── rpi-motion ├── Dockerfile └── motion.conf ├── rpi-mpg123 ├── Dockerfile └── audio.mp3 ├── rpi-multimon-ng └── Dockerfile ├── rpi-neopixel ├── .gitignore ├── Dockerfile ├── LICENSE ├── README.md ├── package.json └── server.js ├── rpi-netcat └── Dockerfile ├── rpi-nginx └── Dockerfile ├── rpi-nmap └── Dockerfile ├── rpi-okular └── Dockerfile ├── rpi-opencv └── Dockerfile ├── rpi-openstf └── Dockerfile ├── rpi-pianobar ├── Dockerfile ├── config └── tls_fingerprint.sh ├── rpi-pifm-rds └── Dockerfile ├── rpi-pifm └── Dockerfile ├── rpi-pirate-radio ├── Dockerfile └── pirateradio.conf ├── rpi-processing └── Dockerfile ├── rpi-pulseaudio ├── Dockerfile ├── client.conf ├── daemon.conf └── default.pa ├── rpi-python └── Dockerfile ├── rpi-radioplayer └── Dockerfile ├── rpi-rethinkdb └── Dockerfile ├── rpi-rpio └── Dockerfile ├── rpi-rpitx └── Dockerfile ├── rpi-rtl-ais └── Dockerfile ├── rpi-sdr └── Dockerfile ├── rpi-synergy └── Dockerfile ├── rpi-tipboard ├── Dockerfile ├── layout_config.yaml ├── settings-local.py └── supervisord.conf ├── rpi-uiautomator-boto └── Dockerfile ├── rpi-uiautomator └── Dockerfile ├── rpi-video-looper └── Dockerfile ├── rpi-vnc └── Dockerfile ├── rpi-webide └── Dockerfile ├── rpi-wiringpi └── Dockerfile └── rpi-x11-apps └── Dockerfile /README.md: -------------------------------------------------------------------------------- 1 | # rpi-dockerfiles 2 | -------------------------------------------------------------------------------- /dockerfunc: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | # bash wrappers for docker run commands 3 | # refs: 4 | # https://github.com/jfrazelle/dotfiles 5 | # https://blog.jessfraz.com/post/docker-containers-on-the-desktop/ 6 | 7 | 8 | 9 | # 10 | # container aliases 11 | # 12 | 13 | # aircraft communication addressing/reporting system 14 | acarsdec(){ 15 | del_stopped acarsdec 16 | 17 | docker run -d \ 18 | --device=/dev/bus/usb \ 19 | --name acarsdec \ 20 | mitchtech/rpi-acarsdec -v -g 450 -r 0 130.025 131.550 21 | } 22 | # amazon alexa client 23 | alexapi(){ 24 | del_stopped alexapi 25 | 26 | docker run -d \ 27 | --net host \ 28 | -p 5000:5000 \ 29 | --device /dev/snd \ 30 | --device=/dev/bus/usb \ 31 | --name alexapi \ 32 | mitchtech/rpi-alexapi 33 | } 34 | # search for files within apt packages 35 | apt_file(){ 36 | docker run --rm -it \ 37 | --name apt-file \ 38 | mitchtech/rpi-apt-file 39 | } 40 | alias apt-file="apt_file" 41 | # adb, fastboot 42 | android-tools(){ 43 | docker run --rm -it \ 44 | --device=/dev/bus/usb \ 45 | --name android-tools \ 46 | mitchtech/rpi-android-tools 47 | } 48 | # arduino 49 | arduino(){ 50 | del_stopped arduino 51 | xhost + 52 | 53 | docker run -d \ 54 | --device=/dev/bus/usb \ 55 | -e DISPLAY=unix:0 \ 56 | -v $PWD:/sketchbook \ 57 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 58 | --name arduino \ 59 | mitchtech/rpi-arduino 60 | } 61 | # beacon bluetooth low energy 62 | # beacon(){} 63 | # cli tool for bladerf sdr 64 | bladerf-cli(){ 65 | docker run -it --rm \ 66 | --device=/dev/bus/usb \ 67 | --name bladerf-cli \ 68 | mitchtech/rpi-bladerf bladeRF-cli -i 69 | } 70 | # video and photo webcam capture 71 | cheese(){ 72 | del_stopped cheese 73 | 74 | docker run -d \ 75 | -v /etc/localtime:/etc/localtime:ro \ 76 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 77 | -e DISPLAY=unix$DISPLAY \ 78 | -v $HOME/Pictures:/root/Pictures \ 79 | --device /dev/video0 \ 80 | --device /dev/snd \ 81 | --device /dev/dri \ 82 | --name cheese \ 83 | mitchtech/rpi-cheese 84 | } 85 | # web browser 86 | # chromium(){} 87 | # movies via nzbs & torrents 88 | couchpotato(){ 89 | del_stopped couchpotato 90 | 91 | docker run -d \ 92 | -v /etc/localtime:/etc/localtime:ro \ 93 | -v $HOME/.sonarr:/config \ 94 | -v $HOME/Downloads:/downloads \ 95 | -v $HOME/movies:/movies \ 96 | -p 5050:5050 \ 97 | --restart=always \ 98 | --name couchpotato \ 99 | mitchtech/rpi-couchpotato 100 | } 101 | # ruby-based web dashboard 102 | dashing(){ 103 | del_stopped dashing 104 | 105 | docker run -d \ 106 | -p 3030:3030 \ 107 | --name dashing \ 108 | mitchtech/rpi-dashing 109 | } 110 | # web interface for docker 111 | dockerui(){ 112 | del_stopped dockerui 113 | 114 | docker run -d \ 115 | -p 9000:9000 \ 116 | -v /var/run/docker.sock:/var/run/docker.sock \ 117 | --name dockerui \ 118 | hypriot/rpi-dockerui 119 | } 120 | # adsb decoder for rtl-sdr 121 | dump1090(){ 122 | del_stopped dump1090 123 | 124 | docker run -d \ 125 | --net host \ 126 | -p 8080:8080 \ 127 | --device=/dev/bus/usb \ 128 | --name dump1090 \ 129 | mitchtech/rpi-dump1090 --interactive --net 130 | } 131 | # dns, dhcp, network infrastructure 132 | dnsmasq(){ 133 | del_stopped dnsmasq 134 | 135 | docker run -d \ 136 | -p=53:53/udp 137 | -v .dnsmasq:/dnsmasq \ 138 | --name dnsmasq \ 139 | mitchtech/rpi-dnsmasq 140 | } 141 | # lightweight web brower 142 | epiphany(){ 143 | del_stopped epiphany 144 | xhost + 145 | 146 | docker run -d \ 147 | --net host \ 148 | -e DISPLAY=unix:0 \ 149 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 150 | --name epiphany \ 151 | mitchtech/rpi-epiphany "$@" 152 | # --privileged \ 153 | # --restart=on-failure:5 \ 154 | } 155 | 156 | # command line text-to-speech 157 | festival(){ 158 | del_stopped festival 159 | 160 | docker run --rm -d \ 161 | --name festival \ 162 | --device /dev/snd \ 163 | mitchtech/rpi-festival \ 164 | echo $@ | festival --tts 165 | #"echo" "$@" "|" "festival" "--tts" 166 | } 167 | # lightweight command line text-to-speech 168 | flite(){ 169 | del_stopped flite 170 | 171 | docker run --rm -d \ 172 | --name festival \ 173 | --device /dev/snd \ 174 | mitchtech/rpi-flite \ 175 | flite -t "$@" 176 | } 177 | # real-time adsb aircraft tracking 178 | # flightaware(){} 179 | # frequency show visual spectrum analyzer 180 | freqshow(){ 181 | docker run --rm -it \ 182 | --privileged \ 183 | --device=/dev/bus/usb \ 184 | -v /var/run/docker.sock:/var/run/docker.sock \ 185 | -e DISPLAY=172.17.42.1:0.0 \ 186 | --name freqshow \ 187 | mitchtech/rpi-freqshow 188 | } 189 | # google talk (xmpp) bot 190 | # gtalkbot(){} 191 | # node.js-based development environment 192 | google-coder(){ 193 | del_stopped google-coder 194 | 195 | docker run -d \ 196 | -p 8080:8080 \ 197 | --name google-coder \ 198 | hypriot/rpi-google-coder 199 | } 200 | # gnuradio suite (osmocom, gqrx) 201 | # gnuradio(){} 202 | # gpio pin mode/state acess 203 | # gpio(){ 204 | # docker run --rm -it \ 205 | # --cap-add SYS_RAWIO \ 206 | # --device /dev/mem \ 207 | # --name gpio \ 208 | # mitchtech/rpi-wiringpi "$@" 209 | # } 210 | # physical gmail notification daemon 211 | # gpio-gmail(){} 212 | # video and photo webcam capture 213 | # guvcview(){} 214 | # wifi access point 215 | # hostapd(){} 216 | # minimal busybox http server 217 | httpd(){ 218 | del_stopped httpd 219 | 220 | docker run -d \ 221 | -p 80:80 \ 222 | --name httpd \ 223 | mitchtech/rpi-busybox-httpd 224 | } 225 | # debian firefox web brower 226 | iceweasel(){ 227 | del_stopped iceweasel 228 | xhost + 229 | 230 | docker run -d \ 231 | --net host \ 232 | -e DISPLAY=unix:0 \ 233 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 234 | --name iceweasel \ 235 | mitchtech/rpi-iceweasel "$@" 236 | # --privileged \ 237 | # --restart=on-failure:5 \ 238 | } 239 | # voice control platform 240 | # jasper(){} 241 | # gsm base station scanner 242 | # kalibrate(){} 243 | # kitematic docker gui 244 | kitematic(){ 245 | del_stopped kitematic 246 | 247 | docker run -d \ 248 | --privileged \ 249 | -v /var/run/docker.sock:/var/run/docker.sock \ 250 | -e DISPLAY=172.17.42.1:0.0 \ 251 | --name kitematic \ 252 | mitchtech/rpi-kitematic 253 | } 254 | # kivy graphic info screen 255 | kivy-infoscreen(){ 256 | del_stopped kivy-infoscreen 257 | 258 | docker run -d \ 259 | --privileged \ 260 | -e DISPLAY=172.17.42.1:0.0 \ 261 | --name kivy-infoscreen \ 262 | mitchtech/rpi-kivy-infoscreen 263 | } 264 | # documents, spreadsheets, and slides 265 | libreoffice(){ 266 | xhost + 267 | del_stopped libreoffice 268 | 269 | docker run -d \ 270 | -v /etc/localtime:/etc/localtime:ro \ 271 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 272 | -e DISPLAY=unix$DISPLAY \ 273 | -v $HOME/slides:/root/slides \ 274 | --name libreoffice \ 275 | mitchtech/rpi-libreoffice 276 | # -e GDK_SCALE \ 277 | # -e GDK_DPI_SCALE \ 278 | } 279 | # text-based web browser 280 | lynx(){ 281 | docker run --rm -it \ 282 | --name lynx \ 283 | mitchtech/rpi-lynx "$@" 284 | } 285 | # lightweight web brower 286 | midori(){ 287 | del_stopped midori 288 | xhost + 289 | 290 | docker run -d \ 291 | --net host \ 292 | -e DISPLAY=unix:0 \ 293 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 294 | --name midori \ 295 | mitchtech/rpi-midori "$@" 296 | # --privileged \ 297 | # --restart=on-failure:5 \ 298 | } 299 | # modulation/demodulation over rf 300 | # minimodem(){} 301 | # webcam and motion detection server 302 | motion(){ 303 | del_stopped motion 304 | 305 | docker run -d \ 306 | --device=/dev/video0 \ 307 | -v $PWD/motion.conf:/etc/motion/motion.conf \ 308 | -p 8080:8080 \ 309 | -p 8081:8081 \ 310 | --name motion \ 311 | mitchtech/rpi-motion 312 | # --privileged \ 313 | # -v ./motion:/var/lib/motion \ 314 | } 315 | # digital transmission decoder/demodulator 316 | # multimon-ng(){} 317 | # text-based audio player 318 | mpg123(){ 319 | docker run --rm -it \ 320 | --privileged \ 321 | --device /dev/snd \ 322 | -v $PWD/audio.mp3:/audio.mp3 \ 323 | -v $PWD:/audio \ 324 | --name mpg123 \ 325 | mitchtech/rpi-mpg123 326 | } 327 | # adafruit neopixel leds 328 | neopixel(){ 329 | del_stopped neopixel 330 | 331 | docker run -d \ 332 | --cap-add SYS_RAWIO \ 333 | --device /dev/mem \ 334 | --name neopixel \ 335 | mitchtech/rpi-neopixel 336 | } 337 | # nintendo emulator 338 | # nes(){} 339 | # read and write tcp/ip connections 340 | netcat(){ 341 | docker run --rm -it \ 342 | --net host \ 343 | mitchtech/rpi-netcat "$@" 344 | } 345 | # web and reverse proxy server 346 | nginx(){ 347 | del_stopped nginx 348 | 349 | docker run -d \ 350 | --restart always \ 351 | -v $HOME/.nginx:/etc/nginx \ 352 | --net host \ 353 | --name nginx \ 354 | mitchtech/rpi-nginx 355 | } 356 | # network map port scanner 357 | nmap(){ 358 | docker run --rm -it \ 359 | --net host \ 360 | mitchtech/rpi-nmap "$@" 361 | } 362 | # pdf viewer and presentation tool 363 | okular(){ 364 | del_stopped okular 365 | xhost + 366 | 367 | docker run -d \ 368 | -e DISPLAY=unix:0 \ 369 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 370 | --name okular \ 371 | mitchtech/rpi-okular "$@" 372 | # --privileged \ 373 | } 374 | # smartphone test farm 375 | # openstf(){} 376 | # computer vision 377 | # opencv(){} 378 | # text-based pandora music 379 | pianobar(){ 380 | docker run --rm -it \ 381 | --privileged \ 382 | --net host \ 383 | --device /dev/snd \ 384 | --name pianobar \ 385 | mitchtech/rpi-pianobar 386 | } 387 | # fm radio transmit pifm(sound_file, frequency) 388 | pifm(){ 389 | del_stopped pifm 390 | local sound_file=$1 391 | local frequency=$2 392 | 393 | docker run -d \ 394 | --cap-add SYS_RAWIO \ 395 | --device /dev/mem \ 396 | --name pifm \ 397 | mitchtech/rpi-pifm ${sound_file} ${frequency} 398 | } 399 | # fm radio playlist broadcast 400 | pirate-radio(){ 401 | del_stopped pirate-radio 402 | 403 | docker run -d \ 404 | --cap-add SYS_RAWIO \ 405 | --device /dev/mem \ 406 | -v $PWD/pirateradio.conf:/pirateradio/pirateradio.conf \ 407 | -v $PWD:/pirateradio \ 408 | --name pirate-radio \ 409 | mitchtech/rpi-pirate-radio 410 | } 411 | # private web proxy 412 | # privoxy(){} 413 | # audio server and proxy 414 | # pulseaudio(){} 415 | # real-time database engine 416 | rethinkdb(){ 417 | del_stopped rethinkdb 418 | 419 | docker run -d \ 420 | -p 8081:8081 \ 421 | -p 28015:28015 \ 422 | -p 29015:29015 \ 423 | -v $PWD:/data \ 424 | --name rethinkdb \ 425 | mitchtech/rpi-rethinkdb 426 | } 427 | # radio transmitter for am, fm, ssb, sstv, fsq, vfo 428 | rpitx(){ 429 | del_stopped rpitx 430 | local sound_file=$1 431 | local frequency=$2 432 | 433 | docker run -d \ 434 | --cap-add SYS_RAWIO \ 435 | --device /dev/mem \ 436 | --name rpitx \ 437 | mitchtech/rpi-rpitx ${sound_file} ${frequency} 438 | } 439 | # rtl-sdr ais boat/ship tracking 440 | rtl-ais(){ 441 | del_stopped rtl-ais 442 | 443 | docker run -d \ 444 | --device=/dev/bus/usb \ 445 | --name rtl-ais \ 446 | mitchtech/rpi-rtl-ais 447 | } 448 | # usenet binary downloader 449 | sabnzbd(){ 450 | del_stopped sabnzbd 451 | 452 | docker run -d \ 453 | -v /etc/localtime:/etc/localtime:ro \ 454 | -v $HOME/.sabnzbd:/config \ 455 | -v $HOME/Downloads:/data \ 456 | -p 8080:8080 \ 457 | --restart=always \ 458 | --name sabnzbd \ 459 | mitchtech/rpi-sabnzbd 460 | } 461 | # pvr for usenet and bittorrent 462 | sickbeard(){ 463 | del_stopped sickbeard 464 | 465 | docker run -d \ 466 | -v /etc/localtime:/etc/localtime:ro \ 467 | -v $HOME/.sickbeard:/config \ 468 | -v $HOME/Downloads:/data/downloads \ 469 | -v $HOME/.nzb:/data/nzb \ 470 | -v $HOME/.torrents:/data/torrents \ 471 | -p 8081:8081 \ 472 | --restart=always \ 473 | --name sickbeard \ 474 | mitchtech/rpi-sickbeard 475 | } 476 | # pvr for usenet and bittorrent 477 | sonarr(){ 478 | del_stopped sonarr 479 | 480 | docker run -d \ 481 | -v /etc/localtime:/etc/localtime:ro \ 482 | -v $HOME/.sonarr:/config \ 483 | -v $HOME/Downloads:/downloads \ 484 | -v $HOME/TV:/tv \ 485 | -p 8080:8080 \ 486 | --name sonarr \ 487 | mitchtech/rpi-sonarr 488 | } 489 | # mouse and keyboard sharing 490 | # synergy 491 | # python-based web dashboard 492 | tipboard(){ 493 | del_stopped tipboard 494 | 495 | docker run -d \ 496 | -p 7272:7272 \ 497 | --name=tipboard \ 498 | mitchtech/rpi-tipboard 499 | # -v $PWD/settings-local.py:/root/.tipboard/settings-local.py \ 500 | # -v $PWD/layout_config.yaml:/root/.tipboard/layout_config.yaml \ 501 | } 502 | # the onion router 503 | # tor(){} 504 | # web browser for tor 505 | # torbrowser(){} 506 | # instant messenger client for tor 507 | # tormessenger(){} 508 | # proxy on top of tor 509 | # torproxy(){} 510 | # bittorrent client 511 | transmission(){ 512 | del_stopped transmission 513 | 514 | docker run -d \ 515 | -v /etc/localtime:/etc/localtime:ro \ 516 | -v $HOME/.transmission:/config \ 517 | -v $HOME/Downloads:/downloads \ 518 | -p 9091:9091 \ 519 | -p 51413:51413 \ 520 | -p 51413:51413/udp \ 521 | --name transmission \ 522 | mitchtech/rpi-transmission 523 | # -v $HOME/Torrents:/transmission/download \ 524 | # -v $HOME/.transmission:/transmission/config \ 525 | # transmission -v pass -u user 526 | } 527 | # android test automation 528 | uiautomator(){ 529 | del_stopped uiautomator 530 | 531 | docker run -d \ 532 | --privileged \ 533 | -p 2222:2222 \ 534 | -v /dev/bus/usb:/dev/bus/usb \ 535 | -v /etc/localtime:/etc/localtime:ro \ 536 | --name uiautomator \ 537 | mitchtech/uiautomator 538 | } 539 | # android test automation x windows 540 | uiautomatorx(){ 541 | del_stopped uiautomator 542 | 543 | docker run -d \ 544 | --privileged \ 545 | -p 2222:2222 \ 546 | -e DISPLAY=$DISPLAY \ 547 | -v /dev/bus/usb:/dev/bus/usb \ 548 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 549 | -v /etc/localtime:/etc/localtime:ro \ 550 | --name uiautomator \ 551 | mitchtech/uiautomator 552 | } 553 | # remote access and control 554 | # vnc(){} 555 | # web browser-based development environment 556 | # webide(){} 557 | # gpio, wiringpi, pyserial 558 | wiringpi(){ 559 | docker run --rm -it \ 560 | --cap-add SYS_RAWIO \ 561 | --device /dev/mem \ 562 | --name wiringpi \ 563 | mitchtech/rpi-wiringpi 564 | } 565 | # x11-apps demo for basic docker x11 setup 566 | xeyes(){ 567 | del_stopped xeyes 568 | 569 | docker run -d \ 570 | --privileged \ 571 | -e DISPLAY=$DISPLAY \ 572 | -v /tmp/.X11-unix:/tmp/.X11-unix \ 573 | --name xeyes \ 574 | mitchtech/x11-apps 575 | } 576 | # sdr base transciever station 577 | yatebts(){ 578 | docker run -it --rm \ 579 | --privileged \ 580 | --device=/dev/bus/usb \ 581 | --net host \ 582 | -v $PWD/ybts.conf:/usr/local/etc/yate/ybts.conf \ 583 | -v $PWD/subscribers.conf:/usr/local/etc/yate/subscribers.conf \ 584 | --name yatebts \ 585 | mitchtech/rpi-bladerf-yatebts 586 | } 587 | 588 | # 589 | # support aliases 590 | # 591 | # kill all running containers 592 | alias docker-killall='docker kill $(docker ps -q)' 593 | 594 | # delete all stopped containers 595 | alias docker-cleanc='printf "\n>>> Deleting stopped containers\n\n" && docker rm $(docker ps -a -q)' 596 | 597 | # delete all untagged images 598 | alias docker-cleani='printf "\n>>> Deleting untagged images\n\n" && docker rmi $(docker images -q -f dangling=true)' 599 | 600 | # delete dangling volumes 601 | alias docker-cleanv='printf "\n>>> Deleting dangling volumes\n\n" && docker volume rm $(docker volume ls -qf dangling=true)' 602 | 603 | # delete stopped containers, untagged images 604 | alias docker-cleanall='dockercleanc || true && dockercleani || true && dockercleanv' 605 | 606 | # removes dangling and exited docker containers 607 | dcleanup(){ 608 | docker rm -v $(docker ps --filter status=exited -q 2>/dev/null) 2>/dev/null 609 | docker rmi $(docker images --filter dangling=true -q 2>/dev/null) 2>/dev/null 610 | } 611 | 612 | # delete stopped container 613 | del_stopped(){ 614 | local name=$1 615 | local state=$(docker inspect --format "{{.State.Running}}" $name 2>/dev/null) 616 | 617 | if [[ "$state" == "false" ]]; then 618 | docker rm $name 619 | fi 620 | } 621 | # dependency on another running container 622 | relies_on(){ 623 | local containers=$@ 624 | 625 | for container in $containers; do 626 | local state=$(docker inspect --format "{{.State.Running}}" $container 2>/dev/null) 627 | 628 | if [[ "$state" == "false" ]] || [[ "$state" == "" ]]; then 629 | echo "$container is not running, starting it for you." 630 | $container 631 | fi 632 | done 633 | } 634 | # enter a running container 635 | enter() { 636 | local name=${1:?} 637 | docker exec -it $name sh -c 'exec $(command -v bash || command -v sh)' 638 | } 639 | # helper to identify running containers 640 | __enter() { 641 | local cur=${COMP_WORDS[COMP_CWORD]} 642 | for cid in $(docker ps -q) 643 | do 644 | local name=$(docker inspect -f '{{.Name}}' $cid) 645 | name=${name#/} 646 | if [[ $name = $cur* ]] 647 | then 648 | COMPREPLY+=("$name") 649 | fi 650 | done 651 | } 652 | # tab completion for entering running containers 653 | complete -F __enter enter -------------------------------------------------------------------------------- /rpi-acarsdec/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | ADD acarsdec-3.2.tar.gz /tmp 6 | 7 | COPY Makefile /tmp/acarsdec-3.2/Makefile 8 | 9 | WORKDIR /tmp/acarsdec-3.2 10 | 11 | RUN make 12 | 13 | ENTRYPOINT ["./acarsdec"] 14 | -------------------------------------------------------------------------------- /rpi-acarsdec/Makefile: -------------------------------------------------------------------------------- 1 | CFLAGS= -Ofast -mfpu=neon-vfpv4 -funroll-loops -pthread -D WITH_RTL -I. 2 | LDLIBS= -lm -pthread -lrtlsdr 3 | 4 | acarsdec: acarsdec.o acars.o msk.o rtl.o air.o output.o alsa.o 5 | $(CC) acarsdec.o acars.o msk.o rtl.o air.o output.o alsa.o -o $@ $(LDLIBS) 6 | 7 | acarsserv: acarsserv.o dbmgn.o 8 | $(CC) -Ofast acarsserv.o dbmgn.o -o $@ -lsqlite3 9 | 10 | acarsdec.o: acarsdec.c acarsdec.h 11 | acars.o: acars.c acarsdec.h syndrom.h 12 | msk.o: msk.c acarsdec.h 13 | output.o: output.c acarsdec.h 14 | rtl.o: rtl.c acarsdec.h 15 | acarsserv.o: acarsserv.h 16 | dbmgm.o: acarsserv.h 17 | 18 | clean: 19 | @rm *.o acarsdec acarsserv 20 | -------------------------------------------------------------------------------- /rpi-acarsdec/acarsdec-3.2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-acarsdec/acarsdec-3.2.tar.gz -------------------------------------------------------------------------------- /rpi-alexa/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-wiringpi 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | libasound2-dev \ 7 | memcached \ 8 | mpg123 \ 9 | python-alsaaudio \ 10 | python-pip \ 11 | --no-install-recommends && \ 12 | rm -rf /var/lib/apt/lists/* 13 | 14 | RUN git clone https://github.com/sammachin/AlexaPi.git && \ 15 | cd AlexaPi && \ 16 | #sed -ni 's/\n/ /g' && \ 17 | pip install -r requirements.txt && \ 18 | touch /var/log/alexa.log 19 | 20 | ADD creds.py /AlexaPi/creds.py 21 | 22 | #RUN ip = `ifconfig eth0 | grep "inet addr" | cut -d ':' -f 2 | cut -d ' ' -f 1` && \ 23 | # python ./auth_web.py && \ 24 | # echo "Open http://$ip:5000" 25 | 26 | WORKDIR /AlexaPi 27 | 28 | CMD ["python", "./auth_web.py"] 29 | -------------------------------------------------------------------------------- /rpi-alexa/creds.py: -------------------------------------------------------------------------------- 1 | import os 2 | 3 | #Alexa Settings 4 | ProductID = "" 5 | Security_Profile_Description ="" 6 | Security_Profile_ID = "" 7 | Client_ID = "" 8 | Client_Secret = "" 9 | 10 | # Alexa Refresh Token 11 | refresh_token = '' 12 | -------------------------------------------------------------------------------- /rpi-android-tools/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | android-tools* \ 7 | ca-certificates \ 8 | curl \ 9 | usbutils \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | # Set up insecure default key 14 | RUN mkdir -m 0750 /root/.android 15 | ADD insecure_shared_adbkey /root/.android/adbkey 16 | ADD insecure_shared_adbkey.pub /root/.android/adbkey.pub 17 | 18 | # Expose default ADB port 19 | EXPOSE 5037 20 | CMD adb -a -P 5037 server nodaemon 21 | -------------------------------------------------------------------------------- /rpi-android-tools/insecure_shared_adbkey: -------------------------------------------------------------------------------- 1 | -----BEGIN PRIVATE KEY----- 2 | MIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQCppPEDWVQFScXE 3 | A/Z5KkDP62pbSSYiFOvpK4ixvAGOoeFD/Jw8m0VtxCsjiXylNaFXA10smHi1Hw3n 4 | vMruEYpQVv3kB4ij0NeZXZ+7jg+lkkQErWiWhACxerOjuOTbnoMtqdDZWwyl1Cd8 5 | ob2AWrVPZmTWoHG8Rw5yrUgDDYMgFMZpmywbXBqpSgw9NdzfLPGuH89LfzpE0hIN 6 | tOsIDjC2GG52h7hTBg6YwtSmFIMO/dk3jEob8eBKVaa5sB19m0POd+9E4Hlo2fEs 7 | +JbnluR7y9YKiTuXZDXTtcvZyg+aIreVtfOzpLbPcBUzBVSIYdc2z+Vq74r/f8pk 8 | QfiCwnHNAgMBAAECggEAZtD44ba6HZpgqjRcpYLeVSWxCDKFUhKsCF3CMzZnGzMx 9 | fCsV5gWVRrmmC5vAV8DxT/NR/T1LqzpvCwx5UWCAG8Edj56hSefBQ8pijSHEiezk 10 | HJGc2dyXLvnW9luRGSoxBvPtCE8Ok1LJu9erKqfPS5gbdZk4VYwbTZWIF5GQ71er 11 | bVS3jwKvqkUgGiZvfVTHmCCx7LGg6vpSS7dfAIPF2lBQfzfIN+epvXhSN8v2w8Lm 12 | 6IYqEI9GVBF7uflk+ogn/2gsZRx2nZzKrPJV1XbHebPOtWNOkDlK+zF8IYAz8e8k 13 | eHBD9DrWX/SlKbklMdGxRqWxayvASSgBjQqjykqKAQKBgQDQkhLkZdpHtLIhZeeB 14 | lwNTrLPiGzg4xMWgeFIMkAxb7ZRWAmbD1OL4OGC+brpb0aQqE2xdlvNcgCq84lof 15 | guLcpu6KJ7qdUzERZicdDtph4NGAKS6djhurHAdQsLaTs6wq57zPWOBYymBAV5TE 16 | 7m5d6/JZsNNEPbaPC8pY8ASsHQKBgQDQOMZ7jibT2gI4fxhCMvGJ6q5tSGKOBozZ 17 | FDcgua2KIqgD73XuW+bAIi/4uPzwvdRUk/quI5ZECfMgNzTLKqOOV/OIz7/ZIduO 18 | gWKM7OskF1JY6ihsTwvVgOUj2TtbZzDZdN1fuUk5FYq4QFr2wXQzlHMSczuAAnEL 19 | kU/dT7kNcQKBgQCLAtDUqY3yfNy8pc7G8H+nJVQ/PyUZsQyHB6qn9NpH6vES4kbb 20 | /ufHyMuyINrUl8Vyxb9UIWfSHxpdCgBHQFUz+47BRfl7IhdyIUOwelXTJqR7ZvdK 21 | y4xlXykA/saxau81KX8OM45Tn47HU5g0KTYmIzxDyzcEJJ2oeZND87UpgQKBgQCR 22 | 3eQ19CyBJu19VJPS9Es/Obd9+UKJik8rV70S4OCQr5ySPTOZiqoJGSoQDM+tet5/ 23 | bbckPOvsuCeo/uOuHC297yE9S4RzgQOFPmCipupHO0tF3Kv6zBlXNVfQmEK70ntn 24 | KzZV88A3DD9Euli/GmDkLW+7khwxngRBfUe8mzfhEQKBgQCSZDQj+luSV3NYoQN8 25 | Uhoz/dpWA1mFYSsRj61K/o0kfscPGoEEhpwJQFIJZBtVaUQlR74nhPBqfk2pHzl/ 26 | LYiHVMKzJ4LZ+60GYay6v2oaL0gXDSc/OiPV1HbvZ6RU4GuuI+5UyeBCyADxN9yE 27 | Ql9mSkxC8xWUlCBzS8Nojdsybw== 28 | -----END PRIVATE KEY----- 29 | -------------------------------------------------------------------------------- /rpi-android-tools/insecure_shared_adbkey.pub: -------------------------------------------------------------------------------- 1 | QAAAAPsciFrNccKC+EFkyn//iu9q5c8212GIVAUzFXDPtqSz87WVtyKaD8rZy7XTNWSXO4kK1st75Jbnlvgs8dloeeBE73fOQ5t9HbC5plVK4PEbSow32f0OgxSm1MKYDgZTuId2bhi2MA4I67QNEtJEOn9Lzx+u8Szf3DU9DEqpGlwbLJtpxhQggw0DSK1yDke8caDWZGZPtVqAvaF8J9SlDFvZ0Kktg57b5Lijs3qxAISWaK0ERJKlD467n12Z19CjiAfk/VZQihHuyrznDR+1eJgsXQNXoTWlfIkjK8RtRZs8nPxD4aGOAbyxiCvp6xQiJklbauvPQCp59gPExUkFVFkD8aSp84VBRBR0aoMw7zpCFsWQeOzuXAdHpWhJDRmaY3+Z835gOd4g4Qo39noyy0bsMEQOlDZNnXE633J5kdm7cqA7R5gFGI421i1wOKzMuHilolYZf0chRDFZXxPgDNunlQecGWHW1upm+O+/6GcXAsiOZcjthcE95FW3G9Psu/c/RhAPCB1dy8yyJGKkNk7n8yXAJbIYsSnhoM39eIcSGbtxxXB27V22n+KuzQRq7FubtYbqO/I+W0YzojuoWLrflwtmtcDPGZgI+pcAhXHpF4zvxOsi3HYemZ4dre3ELjQQ3vGwYRCJ23pqya8ifQxMrzZs7YFT91I/0V03BEquRpYYNgEAAQA= insecure_shared_adbkey -------------------------------------------------------------------------------- /rpi-apt-file/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | apt-file \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN apt-file update 11 | 12 | CMD ["bash"] 13 | -------------------------------------------------------------------------------- /rpi-arduino/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-java 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | arduino \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | ENTRYPOINT ["arduino"] 11 | -------------------------------------------------------------------------------- /rpi-beacon/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:wheezy 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | gcc \ 8 | libusb-dev \ 9 | libdbus-1-dev \ 10 | libglib2.0-dev \ 11 | libudev-dev \ 12 | libical-dev \ 13 | libreadline-dev \ 14 | wget \ 15 | --no-install-recommends && \ 16 | rm -rf /var/lib/apt/lists/* 17 | 18 | RUN wget --no-check-certificate \ 19 | www.kernel.org/pub/linux/bluetooth/bluez-5.11.tar.xz && \ 20 | unxz bluez-5.11.tar.xz && \ 21 | tar xvf bluez-5.11.tar && \ 22 | cd bluez-5.11 && \ 23 | ./configure --disable-systemd && \ 24 | make && \ 25 | make install 26 | 27 | RUN wget --no-check-certificate \ 28 | https://s3.amazonaws.com/plugable/bin/fw-0a5c_21e8.hcd && \ 29 | mkdir -p /lib/firmware/brcm && \ 30 | mv fw-0a5c_21e8.hcd /lib/firmware/brcm/BCM20702A1-0a5c-21e8.hcd 31 | 32 | #WORKDIR /data 33 | 34 | CMD ["/bluez-5.11/tools/hciconfig"] 35 | -------------------------------------------------------------------------------- /rpi-bladerf-yatebts/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-bladerf 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | apache2 \ 7 | automake \ 8 | ca-certificates \ 9 | g++ \ 10 | gcc \ 11 | git \ 12 | make \ 13 | php5 \ 14 | --no-install-recommends \ 15 | && rm -rf /var/lib/apt/lists/* 16 | 17 | RUN git clone https://github.com/evilsocket/evilbts.git && \ 18 | cd evilbts/yate && \ 19 | ./autogen.sh && \ 20 | ./configure --prefix=/usr/local && \ 21 | make -j4 && \ 22 | make install && \ 23 | ldconfig 24 | 25 | RUN cd /evilbts/yatebts && \ 26 | ./autogen.sh && \ 27 | ./configure --prefix=/usr/local && \ 28 | make -j4 && \ 29 | make install && \ 30 | ldconfig && \ 31 | ln -s /usr/local/share/yate/nib_web /var/www/html/nib && \ 32 | chmod a+w -R /usr/local/etc/yate 33 | 34 | EXPOSE 80 35 | 36 | CMD ["yate -s"] 37 | -------------------------------------------------------------------------------- /rpi-bladerf-yatebts/subscribers.conf: -------------------------------------------------------------------------------- 1 | ; !!! NOTE !!! 2 | ; This file is used when YateBTS is in NIB (Network in a box) mode 3 | ; File generated by the YateBTS NIB interface 4 | 5 | [general] 6 | ; Your Country code (where YateBTS is installed) 7 | ; Ex: 1 for US, 44 for UK; http://www.mcc-mnc.com/ 8 | ;country_code= 9 | 10 | ; Subscribers are accepted by either matching the IMSI against this configured 11 | ; regular expression or by setting subscribers individually 12 | ; Note! If a regular expression is used, 2G/3G authentication cannot be used. 13 | ; Ex: regexp=^001 14 | ;regexp= 15 | 16 | ; Resource for the emergency calls gateway 17 | ; If not set any emergency calls will be delivered to the outbound gateway 18 | ; It is also possible to specify a short or international number (possibly MSISDN) 19 | ; Ex: gw_sos=sip/sip:sos@emergency.gw 20 | ; Ex: gw_sos=111 21 | ; Ex: gw_sos=+10744341111 22 | ;gw_sos= 23 | 24 | 25 | ; you have to put subscriber IMSI as a category and the subscriber parameters 26 | ; as keys 27 | 28 | ;[001990010001014] 29 | ; Official phone number. Should include configured country code 30 | ; Ex: msisdn=10744341111 31 | 32 | ; Whether this subscriber is allowed to use the service 33 | ; Allowed values: on, off 34 | ; Ex: active=off 35 | 36 | ; Card secret. Set or generated when SIMs are written 37 | ; Ex:ki=00112233445566778899aabbccddeeff 38 | 39 | ; Operator secret. 40 | ; Allowed values: empty for 2G IMSIs, 00000000000000000000000000000000 for 3G IMSIs. 41 | ; Ex: op=00000000000000000000000000000000 42 | 43 | ; SIM type 44 | ; Allowed values: 2G, 3G 45 | ; Ex: imsi_type=3G 46 | 47 | ; Short number subscribers can use to dial each other. Can be empty or not set 48 | ; Ex:short_number=111 49 | -------------------------------------------------------------------------------- /rpi-bladerf/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | bladerf \ 7 | git \ 8 | libbladerf0 \ 9 | libbladerf-dev \ 10 | --no-install-recommends \ 11 | && rm -rf /var/lib/apt/lists/* 12 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-busybox-httpd 2 | 3 | EXPOSE 80 4 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Hypriot 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | 23 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/Makefile: -------------------------------------------------------------------------------- 1 | DOCKER_IMAGE_VERSION=0.1.1 2 | DOCKER_IMAGE_NAME=mitchtech/rpi-busybox-httpd 3 | DOCKER_IMAGE_TAGNAME=$(DOCKER_IMAGE_NAME):$(DOCKER_IMAGE_VERSION) 4 | 5 | default: build 6 | 7 | build: 8 | dockerize -t $(DOCKER_IMAGE_NAME) \ 9 | --add-file index.html /www/ \ 10 | --add-file pi_armed_with_docker.jpg /www/ \ 11 | --entry '/bin/busybox' \ 12 | --cmd 'httpd -f -p 80 -h /www' \ 13 | /bin/busybox 14 | docker tag -f $(DOCKER_IMAGE_NAME) $(DOCKER_IMAGE_NAME):latest 15 | docker build -t mitchtech/rpi-busybox-httpd . 16 | docker tag -f $(DOCKER_IMAGE_NAME) $(DOCKER_IMAGE_NAME):latest 17 | docker tag -f $(DOCKER_IMAGE_NAME) $(DOCKER_IMAGE_TAGNAME) 18 | 19 | push: 20 | docker push $(DOCKER_IMAGE_NAME) 21 | 22 | test: 23 | docker run --rm mitchtech/rpi-busybox-httpd /bin/busybox echo "Success." 24 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/README.md: -------------------------------------------------------------------------------- 1 | # rpi-busybox-httpd 2 | 3 | Raspberry Pi compatible Docker Image with a minimal `Busybox httpd` web server. 4 | 5 | ## Details 6 | - [Source Project Page](https://github.com/hypriot) 7 | - [Source Repository](https://github.com/hypriot/rpi-busybox-httpd) 8 | 9 | ## Start the default web server 10 | ```bash 11 | docker run -d -p 8080:80 hypriot/rpi-busybox-httpd 12 | ``` 13 | Or use the script `start-webservers.sh count [start]` to start many web servers, port number uses 10000+n 14 | ```bash 15 | ./start-webservers.sh 5 16 | ./start-webservers.sh 10 5 17 | ``` 18 | 19 | ## How to create this image 20 | 21 | Run all the commands from within the project root directory. 22 | 23 | This Docker Image is extremely small (approx. 2.1MByte) and will be build with the tool [dockerize](https://github.com/larsks/dockerize). 24 | 25 | ### Install the build dependencies first 26 | ```bash 27 | ./install-deps.sh 28 | ``` 29 | 30 | ### Build the Docker Image 31 | ```bash 32 | make build 33 | ``` 34 | 35 | #### Test the Docker Image 36 | ```bash 37 | make test 38 | ``` 39 | 40 | #### Push the Docker Image to the Docker Hub 41 | * First use a `docker login` with username, password and email address 42 | * Second push the Docker Image to the official Docker Hub 43 | 44 | ```bash 45 | make push 46 | ``` 47 | 48 | ## License 49 | 50 | The MIT License (MIT) 51 | 52 | Copyright (c) 2015 Hypriot 53 | 54 | Permission is hereby granted, free of charge, to any person obtaining a copy 55 | of this software and associated documentation files (the "Software"), to deal 56 | in the Software without restriction, including without limitation the rights 57 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 58 | copies of the Software, and to permit persons to whom the Software is 59 | furnished to do so, subject to the following conditions: 60 | 61 | The above copyright notice and this permission notice shall be included in all 62 | copies or substantial portions of the Software. 63 | 64 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 65 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 66 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 67 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 68 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 69 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 70 | SOFTWARE. 71 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/dockerize-busybox-httpd.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e 3 | 4 | dockerize -t mitchtech/rpi-busybox-httpd \ 5 | --add-file index.html /www/ \ 6 | --add-file pi_armed_with_docker.jpg /www/ \ 7 | --entry '/bin/busybox' \ 8 | --cmd 'httpd -f -p 80 -h /www' \ 9 | /bin/busybox 10 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/index.html: -------------------------------------------------------------------------------- 1 | 2 | Pi armed with Docker by Hypriot 3 | 4 |
5 | pi armed with docker 6 |
7 | 8 | 9 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/install-deps.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | sudo apt-get install -y make busybox python-dev python-pip 4 | sudo pip install https://github.com/larsks/dockerize/archive/master.zip 5 | -------------------------------------------------------------------------------- /rpi-busybox-httpd/pi_armed_with_docker.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-busybox-httpd/pi_armed_with_docker.jpg -------------------------------------------------------------------------------- /rpi-busybox-httpd/start-webservers.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e 3 | 4 | DOCKER_IMAGE="mitchtech/rpi-busybox-httpd" 5 | P1=$1 6 | P2=$2 7 | MAXNR=${P1:="1"} 8 | STARTNR=${P2:="0"} 9 | 10 | COUNTER=$STARTNR 11 | while [ $COUNTER -lt $MAXNR ]; do 12 | let COUNTER=COUNTER+1 13 | let PORT=10000+COUNTER 14 | echo COUNTER=$COUNTER, PORT=$PORT 15 | docker run -d --name=WebServer-$PORT -p $PORT:80 $DOCKER_IMAGE 16 | done 17 | -------------------------------------------------------------------------------- /rpi-cheese/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | cheese \ 7 | libgl1-mesa-dri \ 8 | libgl1-mesa-glx \ 9 | --no-install-recommends \ 10 | && rm -rf /var/lib/apt/lists/* 11 | 12 | ENTRYPOINT ["cheese"] 13 | -------------------------------------------------------------------------------- /rpi-chromium/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | curl \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN curl -sSL https://github.com/hypriot/x11-on-HypriotOS/raw/master/install-chromium-browser.sh | bash 11 | 12 | ENTRYPOINT ["chromium-browser"] 13 | 14 | -------------------------------------------------------------------------------- /rpi-dashing/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-ruby:2.2.2 2 | 3 | RUN apt-get update && apt-get install -y -q \ 4 | build-essential \ 5 | curl \ 6 | python \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN curl -sL https://deb.nodesource.com/setup_5.x | bash - 11 | 12 | RUN apt-get install -y nodejs 13 | 14 | RUN mkdir -p /usr/src/app 15 | 16 | COPY ./dashboard/ /usr/src/app 17 | 18 | WORKDIR /usr/src/app 19 | 20 | RUN bundle install 21 | 22 | CMD ["dashing", "start"] 23 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/.gitignore: -------------------------------------------------------------------------------- 1 | *DS_STORE 2 | history.yml 3 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/Gemfile: -------------------------------------------------------------------------------- 1 | source 'https://rubygems.org' 2 | 3 | gem 'dashing' 4 | 5 | ## Remove this if you don't need a twitter widget. 6 | gem 'twitter', '>= 5.9.0' -------------------------------------------------------------------------------- /rpi-dashing/dashboard/Gemfile.lock: -------------------------------------------------------------------------------- 1 | GEM 2 | remote: https://rubygems.org/ 3 | specs: 4 | addressable (2.3.8) 5 | backports (3.6.7) 6 | buftok (0.2.0) 7 | coffee-script (2.2.0) 8 | coffee-script-source 9 | execjs 10 | coffee-script-source (1.10.0) 11 | daemons (1.2.3) 12 | dashing (1.3.4) 13 | coffee-script (~> 2.2.0) 14 | execjs (~> 2.0.2) 15 | rack (~> 1.5.2) 16 | rufus-scheduler (~> 2.0.24) 17 | sass (~> 3.2.12) 18 | sinatra (~> 1.4.4) 19 | sinatra-contrib (~> 1.4.2) 20 | sprockets (~> 2.10.1) 21 | thin (~> 1.6.1) 22 | thor (~> 0.18.1) 23 | domain_name (0.5.25) 24 | unf (>= 0.0.5, < 1.0.0) 25 | equalizer (0.0.10) 26 | eventmachine (1.0.8) 27 | execjs (2.0.2) 28 | faraday (0.9.2) 29 | multipart-post (>= 1.2, < 3) 30 | hike (1.2.3) 31 | http (0.9.8) 32 | addressable (~> 2.3) 33 | http-cookie (~> 1.0) 34 | http-form_data (~> 1.0.1) 35 | http_parser.rb (~> 0.6.0) 36 | http-cookie (1.0.2) 37 | domain_name (~> 0.5) 38 | http-form_data (1.0.1) 39 | http_parser.rb (0.6.0) 40 | json (1.8.3) 41 | memoizable (0.4.2) 42 | thread_safe (~> 0.3, >= 0.3.1) 43 | multi_json (1.11.2) 44 | multipart-post (2.0.0) 45 | naught (1.1.0) 46 | rack (1.5.5) 47 | rack-protection (1.5.3) 48 | rack 49 | rack-test (0.6.3) 50 | rack (>= 1.0) 51 | rufus-scheduler (2.0.24) 52 | tzinfo (>= 0.3.22) 53 | sass (3.2.19) 54 | simple_oauth (0.3.1) 55 | sinatra (1.4.6) 56 | rack (~> 1.4) 57 | rack-protection (~> 1.4) 58 | tilt (>= 1.3, < 3) 59 | sinatra-contrib (1.4.6) 60 | backports (>= 2.0) 61 | multi_json 62 | rack-protection 63 | rack-test 64 | sinatra (~> 1.4.0) 65 | tilt (>= 1.3, < 3) 66 | sprockets (2.10.2) 67 | hike (~> 1.2) 68 | multi_json (~> 1.0) 69 | rack (~> 1.0) 70 | tilt (~> 1.1, != 1.3.0) 71 | thin (1.6.4) 72 | daemons (~> 1.0, >= 1.0.9) 73 | eventmachine (~> 1.0, >= 1.0.4) 74 | rack (~> 1.0) 75 | thor (0.18.1) 76 | thread_safe (0.3.5) 77 | tilt (1.4.1) 78 | twitter (5.15.0) 79 | addressable (~> 2.3) 80 | buftok (~> 0.2.0) 81 | equalizer (= 0.0.10) 82 | faraday (~> 0.9.0) 83 | http (>= 0.4, < 0.10) 84 | http_parser.rb (~> 0.6.0) 85 | json (~> 1.8) 86 | memoizable (~> 0.4.0) 87 | naught (~> 1.0) 88 | simple_oauth (~> 0.3.0) 89 | tzinfo (1.2.2) 90 | thread_safe (~> 0.1) 91 | unf (0.1.4) 92 | unf_ext 93 | unf_ext (0.0.7.1) 94 | 95 | PLATFORMS 96 | ruby 97 | 98 | DEPENDENCIES 99 | dashing 100 | twitter (>= 5.9.0) 101 | 102 | BUNDLED WITH 103 | 1.10.6 104 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/README.md: -------------------------------------------------------------------------------- 1 | Check out http://shopify.github.com/dashing for more information. -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.eot -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.ttf -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-dashing/dashboard/assets/fonts/fontawesome-webfont.woff -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/images/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-dashing/dashboard/assets/images/logo.png -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/javascripts/application.coffee: -------------------------------------------------------------------------------- 1 | # dashing.js is located in the dashing framework 2 | # It includes jquery & batman for you. 3 | #= require dashing.js 4 | 5 | #= require_directory . 6 | #= require_tree ../../widgets 7 | 8 | console.log("Yeah! The dashboard has started!") 9 | 10 | Dashing.on 'ready', -> 11 | Dashing.widget_margins ||= [5, 5] 12 | Dashing.widget_base_dimensions ||= [300, 360] 13 | Dashing.numColumns ||= 4 14 | 15 | contentWidth = (Dashing.widget_base_dimensions[0] + Dashing.widget_margins[0] * 2) * Dashing.numColumns 16 | 17 | Batman.setImmediate -> 18 | $('.gridster').width(contentWidth) 19 | $('.gridster ul:first').gridster 20 | widget_margins: Dashing.widget_margins 21 | widget_base_dimensions: Dashing.widget_base_dimensions 22 | avoid_overlapped_widgets: !Dashing.customGridsterLayout 23 | draggable: 24 | stop: Dashing.showGridsterInstructions 25 | start: -> Dashing.currentWidgetPositions = Dashing.getWidgetPositions() 26 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/javascripts/dashing.gridster.coffee: -------------------------------------------------------------------------------- 1 | #= require_directory ./gridster 2 | 3 | # This file enables gridster integration (http://gridster.net/) 4 | # Delete it if you'd rather handle the layout yourself. 5 | # You'll miss out on a lot if you do, but we won't hold it against you. 6 | 7 | Dashing.gridsterLayout = (positions) -> 8 | Dashing.customGridsterLayout = true 9 | positions = positions.replace(/^"|"$/g, '') 10 | positions = $.parseJSON(positions) 11 | widgets = $("[data-row^=]") 12 | for widget, index in widgets 13 | $(widget).attr('data-row', positions[index].row) 14 | $(widget).attr('data-col', positions[index].col) 15 | 16 | Dashing.getWidgetPositions = -> 17 | $(".gridster ul:first").gridster().data('gridster').serialize() 18 | 19 | Dashing.showGridsterInstructions = -> 20 | newWidgetPositions = Dashing.getWidgetPositions() 21 | 22 | unless JSON.stringify(newWidgetPositions) == JSON.stringify(Dashing.currentWidgetPositions) 23 | Dashing.currentWidgetPositions = newWidgetPositions 24 | $('#save-gridster').slideDown() 25 | $('#gridster-code').text(" 26 | 31 | ") 32 | 33 | $ -> 34 | $('#save-gridster').leanModal() 35 | 36 | $('#save-gridster').click -> 37 | $('#save-gridster').slideUp() 38 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/javascripts/gridster/jquery.leanModal.min.js: -------------------------------------------------------------------------------- 1 | // leanModal v1.1 by Ray Stone - http://finelysliced.com.au 2 | // Dual licensed under the MIT and GPL 3 | 4 | (function($){$.fn.extend({leanModal:function(options){var defaults={top:100,overlay:0.5,closeButton:null};var overlay=$("
");$("body").append(overlay);options=$.extend(defaults,options);return this.each(function(){var o=options;$(this).click(function(e){var modal_id=$(this).attr("href");$("#lean_overlay").click(function(){close_modal(modal_id)});$(o.closeButton).click(function(){close_modal(modal_id)});var modal_height=$(modal_id).outerHeight();var modal_width=$(modal_id).outerWidth(); 5 | $("#lean_overlay").css({"display":"block",opacity:0});$("#lean_overlay").fadeTo(200,o.overlay);$(modal_id).css({"display":"block","position":"fixed","opacity":0,"z-index":11000,"left":50+"%","margin-left":-(modal_width/2)+"px","top":o.top+"px"});$(modal_id).fadeTo(200,1);e.preventDefault()})});function close_modal(modal_id){$("#lean_overlay").fadeOut(200);$(modal_id).css({"display":"none"})}}})})(jQuery); 6 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/javascripts/jquery.knob.js: -------------------------------------------------------------------------------- 1 | /*!jQuery Knob*/ 2 | /** 3 | * Downward compatible, touchable dial 4 | * 5 | * Version: 1.2.0 (15/07/2012) 6 | * Requires: jQuery v1.7+ 7 | * 8 | * Copyright (c) 2012 Anthony Terrien 9 | * Under MIT and GPL licenses: 10 | * http://www.opensource.org/licenses/mit-license.php 11 | * http://www.gnu.org/licenses/gpl.html 12 | * 13 | * Thanks to vor, eskimoblood, spiffistan, FabrizioC 14 | */ 15 | $(function () { 16 | 17 | /** 18 | * Kontrol library 19 | */ 20 | "use strict"; 21 | 22 | /** 23 | * Definition of globals and core 24 | */ 25 | var k = {}, // kontrol 26 | max = Math.max, 27 | min = Math.min; 28 | 29 | k.c = {}; 30 | k.c.d = $(document); 31 | k.c.t = function (e) { 32 | return e.originalEvent.touches.length - 1; 33 | }; 34 | 35 | /** 36 | * Kontrol Object 37 | * 38 | * Definition of an abstract UI control 39 | * 40 | * Each concrete component must call this one. 41 | * 42 | * k.o.call(this); 43 | * 44 | */ 45 | k.o = function () { 46 | var s = this; 47 | 48 | this.o = null; // array of options 49 | this.$ = null; // jQuery wrapped element 50 | this.i = null; // mixed HTMLInputElement or array of HTMLInputElement 51 | this.g = null; // 2D graphics context for 'pre-rendering' 52 | this.v = null; // value ; mixed array or integer 53 | this.cv = null; // change value ; not commited value 54 | this.x = 0; // canvas x position 55 | this.y = 0; // canvas y position 56 | this.$c = null; // jQuery canvas element 57 | this.c = null; // rendered canvas context 58 | this.t = 0; // touches index 59 | this.isInit = false; 60 | this.fgColor = null; // main color 61 | this.pColor = null; // previous color 62 | this.dH = null; // draw hook 63 | this.cH = null; // change hook 64 | this.eH = null; // cancel hook 65 | this.rH = null; // release hook 66 | 67 | this.run = function () { 68 | var cf = function (e, conf) { 69 | var k; 70 | for (k in conf) { 71 | s.o[k] = conf[k]; 72 | } 73 | s.init(); 74 | s._configure() 75 | ._draw(); 76 | }; 77 | 78 | if(this.$.data('kontroled')) return; 79 | this.$.data('kontroled', true); 80 | 81 | this.extend(); 82 | this.o = $.extend( 83 | { 84 | // Config 85 | min : this.$.data('min') || 0, 86 | max : this.$.data('max') || 100, 87 | stopper : true, 88 | readOnly : this.$.data('readonly'), 89 | 90 | // UI 91 | cursor : (this.$.data('cursor') === true && 30) 92 | || this.$.data('cursor') 93 | || 0, 94 | thickness : this.$.data('thickness') || 0.35, 95 | width : this.$.data('width') || 200, 96 | height : this.$.data('height') || 200, 97 | displayInput : this.$.data('displayinput') == null || this.$.data('displayinput'), 98 | displayPrevious : this.$.data('displayprevious'), 99 | fgColor : this.$.data('fgcolor') || '#87CEEB', 100 | inline : false, 101 | 102 | // Hooks 103 | draw : null, // function () {} 104 | change : null, // function (value) {} 105 | cancel : null, // function () {} 106 | release : null // function (value) {} 107 | }, this.o 108 | ); 109 | 110 | // routing value 111 | if(this.$.is('fieldset')) { 112 | 113 | // fieldset = array of integer 114 | this.v = {}; 115 | this.i = this.$.find('input') 116 | this.i.each(function(k) { 117 | var $this = $(this); 118 | s.i[k] = $this; 119 | s.v[k] = $this.val(); 120 | 121 | $this.bind( 122 | 'change' 123 | , function () { 124 | var val = {}; 125 | val[k] = $this.val(); 126 | s.val(val); 127 | } 128 | ); 129 | }); 130 | this.$.find('legend').remove(); 131 | 132 | } else { 133 | // input = integer 134 | this.i = this.$; 135 | this.v = this.$.val(); 136 | (this.v == '') && (this.v = this.o.min); 137 | 138 | this.$.bind( 139 | 'change' 140 | , function () { 141 | s.val(s.$.val()); 142 | } 143 | ); 144 | } 145 | 146 | (!this.o.displayInput) && this.$.hide(); 147 | 148 | this.$c = $(''); 151 | this.c = this.$c[0].getContext("2d"); 152 | 153 | this.$ 154 | .wrap($('
')) 157 | .before(this.$c); 158 | 159 | if (this.v instanceof Object) { 160 | this.cv = {}; 161 | this.copy(this.v, this.cv); 162 | } else { 163 | this.cv = this.v; 164 | } 165 | 166 | this.$ 167 | .bind("configure", cf) 168 | .parent() 169 | .bind("configure", cf); 170 | 171 | this._listen() 172 | ._configure() 173 | ._xy() 174 | .init(); 175 | 176 | this.isInit = true; 177 | 178 | this._draw(); 179 | 180 | return this; 181 | }; 182 | 183 | this._draw = function () { 184 | 185 | // canvas pre-rendering 186 | var d = true, 187 | c = document.createElement('canvas'); 188 | 189 | c.width = s.o.width; 190 | c.height = s.o.height; 191 | s.g = c.getContext('2d'); 192 | 193 | s.clear(); 194 | 195 | s.dH 196 | && (d = s.dH()); 197 | 198 | (d !== false) && s.draw(); 199 | 200 | s.c.drawImage(c, 0, 0); 201 | c = null; 202 | }; 203 | 204 | this._touch = function (e) { 205 | 206 | var touchMove = function (e) { 207 | 208 | var v = s.xy2val( 209 | e.originalEvent.touches[s.t].pageX, 210 | e.originalEvent.touches[s.t].pageY 211 | ); 212 | 213 | if (v == s.cv) return; 214 | 215 | if ( 216 | s.cH 217 | && (s.cH(v) === false) 218 | ) return; 219 | 220 | 221 | s.change(v); 222 | s._draw(); 223 | }; 224 | 225 | // get touches index 226 | this.t = k.c.t(e); 227 | 228 | // First touch 229 | touchMove(e); 230 | 231 | // Touch events listeners 232 | k.c.d 233 | .bind("touchmove.k", touchMove) 234 | .bind( 235 | "touchend.k" 236 | , function () { 237 | k.c.d.unbind('touchmove.k touchend.k'); 238 | 239 | if ( 240 | s.rH 241 | && (s.rH(s.cv) === false) 242 | ) return; 243 | 244 | s.val(s.cv); 245 | } 246 | ); 247 | 248 | return this; 249 | }; 250 | 251 | this._mouse = function (e) { 252 | 253 | var mouseMove = function (e) { 254 | var v = s.xy2val(e.pageX, e.pageY); 255 | if (v == s.cv) return; 256 | 257 | if ( 258 | s.cH 259 | && (s.cH(v) === false) 260 | ) return; 261 | 262 | s.change(v); 263 | s._draw(); 264 | }; 265 | 266 | // First click 267 | mouseMove(e); 268 | 269 | // Mouse events listeners 270 | k.c.d 271 | .bind("mousemove.k", mouseMove) 272 | .bind( 273 | // Escape key cancel current change 274 | "keyup.k" 275 | , function (e) { 276 | if (e.keyCode === 27) { 277 | k.c.d.unbind("mouseup.k mousemove.k keyup.k"); 278 | 279 | if ( 280 | s.eH 281 | && (s.eH() === false) 282 | ) return; 283 | 284 | s.cancel(); 285 | } 286 | } 287 | ) 288 | .bind( 289 | "mouseup.k" 290 | , function (e) { 291 | k.c.d.unbind('mousemove.k mouseup.k keyup.k'); 292 | 293 | if ( 294 | s.rH 295 | && (s.rH(s.cv) === false) 296 | ) return; 297 | 298 | s.val(s.cv); 299 | } 300 | ); 301 | 302 | return this; 303 | }; 304 | 305 | this._xy = function () { 306 | var o = this.$c.offset(); 307 | this.x = o.left; 308 | this.y = o.top; 309 | return this; 310 | }; 311 | 312 | this._listen = function () { 313 | 314 | if (!this.o.readOnly) { 315 | this.$c 316 | .bind( 317 | "mousedown" 318 | , function (e) { 319 | e.preventDefault(); 320 | s._xy()._mouse(e); 321 | } 322 | ) 323 | .bind( 324 | "touchstart" 325 | , function (e) { 326 | e.preventDefault(); 327 | s._xy()._touch(e); 328 | } 329 | ); 330 | this.listen(); 331 | } else { 332 | this.$.attr('readonly', 'readonly'); 333 | } 334 | 335 | return this; 336 | }; 337 | 338 | this._configure = function () { 339 | 340 | // Hooks 341 | if (this.o.draw) this.dH = this.o.draw; 342 | if (this.o.change) this.cH = this.o.change; 343 | if (this.o.cancel) this.eH = this.o.cancel; 344 | if (this.o.release) this.rH = this.o.release; 345 | 346 | if (this.o.displayPrevious) { 347 | this.pColor = this.h2rgba(this.o.fgColor, "0.4"); 348 | this.fgColor = this.h2rgba(this.o.fgColor, "0.6"); 349 | } else { 350 | this.fgColor = this.o.fgColor; 351 | } 352 | 353 | return this; 354 | }; 355 | 356 | this._clear = function () { 357 | this.$c[0].width = this.$c[0].width; 358 | }; 359 | 360 | // Abstract methods 361 | this.listen = function () {}; // on start, one time 362 | this.extend = function () {}; // each time configure triggered 363 | this.init = function () {}; // each time configure triggered 364 | this.change = function (v) {}; // on change 365 | this.val = function (v) {}; // on release 366 | this.xy2val = function (x, y) {}; // 367 | this.draw = function () {}; // on change / on release 368 | this.clear = function () { this._clear(); }; 369 | 370 | // Utils 371 | this.h2rgba = function (h, a) { 372 | var rgb; 373 | h = h.substring(1,7) 374 | rgb = [parseInt(h.substring(0,2),16) 375 | ,parseInt(h.substring(2,4),16) 376 | ,parseInt(h.substring(4,6),16)]; 377 | return "rgba(" + rgb[0] + "," + rgb[1] + "," + rgb[2] + "," + a + ")"; 378 | }; 379 | 380 | this.copy = function (f, t) { 381 | for (var i in f) { t[i] = f[i]; } 382 | }; 383 | }; 384 | 385 | 386 | /** 387 | * k.Dial 388 | */ 389 | k.Dial = function () { 390 | k.o.call(this); 391 | 392 | this.startAngle = null; 393 | this.xy = null; 394 | this.radius = null; 395 | this.lineWidth = null; 396 | this.cursorExt = null; 397 | this.w2 = null; 398 | this.PI2 = 2*Math.PI; 399 | 400 | this.extend = function () { 401 | this.o = $.extend( 402 | { 403 | bgColor : this.$.data('bgcolor') || '#EEEEEE', 404 | angleOffset : this.$.data('angleoffset') || 0, 405 | angleArc : this.$.data('anglearc') || 360, 406 | inline : true 407 | }, this.o 408 | ); 409 | }; 410 | 411 | this.val = function (v) { 412 | if (null != v) { 413 | this.cv = this.o.stopper ? max(min(v, this.o.max), this.o.min) : v; 414 | this.v = this.cv; 415 | this.$.val(this.v); 416 | this._draw(); 417 | } else { 418 | return this.v; 419 | } 420 | }; 421 | 422 | this.xy2val = function (x, y) { 423 | var a, ret; 424 | 425 | a = Math.atan2( 426 | x - (this.x + this.w2) 427 | , - (y - this.y - this.w2) 428 | ) - this.angleOffset; 429 | 430 | if(this.angleArc != this.PI2 && (a < 0) && (a > -0.5)) { 431 | // if isset angleArc option, set to min if .5 under min 432 | a = 0; 433 | } else if (a < 0) { 434 | a += this.PI2; 435 | } 436 | 437 | ret = ~~ (0.5 + (a * (this.o.max - this.o.min) / this.angleArc)) 438 | + this.o.min; 439 | 440 | this.o.stopper 441 | && (ret = max(min(ret, this.o.max), this.o.min)); 442 | 443 | return ret; 444 | }; 445 | 446 | this.listen = function () { 447 | // bind MouseWheel 448 | var s = this, 449 | mw = function (e) { 450 | e.preventDefault(); 451 | 452 | var ori = e.originalEvent 453 | ,deltaX = ori.detail || ori.wheelDeltaX 454 | ,deltaY = ori.detail || ori.wheelDeltaY 455 | ,v = parseInt(s.$.val()) + (deltaX>0 || deltaY>0 ? 1 : deltaX<0 || deltaY<0 ? -1 : 0); 456 | 457 | if ( 458 | s.cH 459 | && (s.cH(v) === false) 460 | ) return; 461 | 462 | s.val(v); 463 | } 464 | , kval, to, m = 1, kv = {37:-1, 38:1, 39:1, 40:-1}; 465 | 466 | this.$ 467 | .bind( 468 | "keydown" 469 | ,function (e) { 470 | var kc = e.keyCode; 471 | kval = parseInt(String.fromCharCode(kc)); 472 | 473 | if (isNaN(kval)) { 474 | 475 | (kc !== 13) // enter 476 | && (kc !== 8) // bs 477 | && (kc !== 9) // tab 478 | && (kc !== 189) // - 479 | && e.preventDefault(); 480 | 481 | // arrows 482 | if ($.inArray(kc,[37,38,39,40]) > -1) { 483 | e.preventDefault(); 484 | 485 | var v = parseInt(s.$.val()) + kv[kc] * m; 486 | 487 | s.o.stopper 488 | && (v = max(min(v, s.o.max), s.o.min)); 489 | 490 | s.change(v); 491 | s._draw(); 492 | 493 | // long time keydown speed-up 494 | to = window.setTimeout( 495 | function () { m*=2; } 496 | ,30 497 | ); 498 | } 499 | } 500 | } 501 | ) 502 | .bind( 503 | "keyup" 504 | ,function (e) { 505 | if (isNaN(kval)) { 506 | if (to) { 507 | window.clearTimeout(to); 508 | to = null; 509 | m = 1; 510 | s.val(s.$.val()); 511 | } 512 | } else { 513 | // kval postcond 514 | (s.$.val() > s.o.max && s.$.val(s.o.max)) 515 | || (s.$.val() < s.o.min && s.$.val(s.o.min)); 516 | } 517 | 518 | } 519 | ); 520 | 521 | this.$c.bind("mousewheel DOMMouseScroll", mw); 522 | this.$.bind("mousewheel DOMMouseScroll", mw) 523 | }; 524 | 525 | this.init = function () { 526 | 527 | if ( 528 | this.v < this.o.min 529 | || this.v > this.o.max 530 | ) this.v = this.o.min; 531 | 532 | this.$.val(this.v); 533 | this.w2 = this.o.width / 2; 534 | this.cursorExt = this.o.cursor / 100; 535 | this.xy = this.w2; 536 | this.lineWidth = this.xy * this.o.thickness; 537 | this.radius = this.xy - this.lineWidth / 2; 538 | 539 | this.o.angleOffset 540 | && (this.o.angleOffset = isNaN(this.o.angleOffset) ? 0 : this.o.angleOffset); 541 | 542 | this.o.angleArc 543 | && (this.o.angleArc = isNaN(this.o.angleArc) ? this.PI2 : this.o.angleArc); 544 | 545 | // deg to rad 546 | this.angleOffset = this.o.angleOffset * Math.PI / 180; 547 | this.angleArc = this.o.angleArc * Math.PI / 180; 548 | 549 | // compute start and end angles 550 | this.startAngle = 1.5 * Math.PI + this.angleOffset; 551 | this.endAngle = 1.5 * Math.PI + this.angleOffset + this.angleArc; 552 | 553 | var s = max( 554 | String(Math.abs(this.o.max)).length 555 | , String(Math.abs(this.o.min)).length 556 | , 2 557 | ) + 2; 558 | 559 | this.o.displayInput 560 | && this.i.css({ 561 | 'width' : ((this.o.width / 2 + 4) >> 0) + 'px' 562 | ,'height' : ((this.o.width / 3) >> 0) + 'px' 563 | ,'position' : 'absolute' 564 | ,'vertical-align' : 'middle' 565 | ,'margin-top' : ((this.o.width / 3) >> 0) + 'px' 566 | ,'margin-left' : '-' + ((this.o.width * 3 / 4 + 2) >> 0) + 'px' 567 | ,'border' : 0 568 | ,'background' : 'none' 569 | ,'font' : 'bold ' + ((this.o.width / s) >> 0) + 'px Arial' 570 | ,'text-align' : 'center' 571 | ,'color' : this.o.fgColor 572 | ,'padding' : '0px' 573 | ,'-webkit-appearance': 'none' 574 | }) 575 | || this.i.css({ 576 | 'width' : '0px' 577 | ,'visibility' : 'hidden' 578 | }); 579 | }; 580 | 581 | this.change = function (v) { 582 | this.cv = v; 583 | this.$.val(v); 584 | }; 585 | 586 | this.angle = function (v) { 587 | return (v - this.o.min) * this.angleArc / (this.o.max - this.o.min); 588 | }; 589 | 590 | this.draw = function () { 591 | 592 | var c = this.g, // context 593 | a = this.angle(this.cv) // Angle 594 | , sat = this.startAngle // Start angle 595 | , eat = sat + a // End angle 596 | , sa, ea // Previous angles 597 | , r = 1; 598 | 599 | c.lineWidth = this.lineWidth; 600 | 601 | this.o.cursor 602 | && (sat = eat - this.cursorExt) 603 | && (eat = eat + this.cursorExt); 604 | 605 | c.beginPath(); 606 | c.strokeStyle = this.o.bgColor; 607 | c.arc(this.xy, this.xy, this.radius, this.endAngle, this.startAngle, true); 608 | c.stroke(); 609 | 610 | if (this.o.displayPrevious) { 611 | ea = this.startAngle + this.angle(this.v); 612 | sa = this.startAngle; 613 | this.o.cursor 614 | && (sa = ea - this.cursorExt) 615 | && (ea = ea + this.cursorExt); 616 | 617 | c.beginPath(); 618 | c.strokeStyle = this.pColor; 619 | c.arc(this.xy, this.xy, this.radius, sa, ea, false); 620 | c.stroke(); 621 | r = (this.cv == this.v); 622 | } 623 | 624 | c.beginPath(); 625 | c.strokeStyle = r ? this.o.fgColor : this.fgColor ; 626 | c.arc(this.xy, this.xy, this.radius, sat, eat, false); 627 | c.stroke(); 628 | }; 629 | 630 | this.cancel = function () { 631 | this.val(this.v); 632 | }; 633 | }; 634 | 635 | $.fn.dial = $.fn.knob = function (o) { 636 | return this.each( 637 | function () { 638 | var d = new k.Dial(); 639 | d.o = o; 640 | d.$ = $(this); 641 | d.run(); 642 | } 643 | ).parent(); 644 | }; 645 | 646 | }); -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/stylesheets/application.scss: -------------------------------------------------------------------------------- 1 | /* 2 | //=require_directory . 3 | //=require_tree ../../widgets 4 | */ 5 | // ---------------------------------------------------------------------------- 6 | // Sass declarations 7 | // ---------------------------------------------------------------------------- 8 | $background-color: #222; 9 | $text-color: #fff; 10 | 11 | $background-warning-color-1: #e82711; 12 | $background-warning-color-2: #9b2d23; 13 | $text-warning-color: #fff; 14 | 15 | $background-danger-color-1: #eeae32; 16 | $background-danger-color-2: #ff9618; 17 | $text-danger-color: #fff; 18 | 19 | @-webkit-keyframes status-warning-background { 20 | 0% { background-color: $background-warning-color-1; } 21 | 50% { background-color: $background-warning-color-2; } 22 | 100% { background-color: $background-warning-color-1; } 23 | } 24 | @-webkit-keyframes status-danger-background { 25 | 0% { background-color: $background-danger-color-1; } 26 | 50% { background-color: $background-danger-color-2; } 27 | 100% { background-color: $background-danger-color-1; } 28 | } 29 | @mixin animation($animation-name, $duration, $function, $animation-iteration-count:""){ 30 | -webkit-animation: $animation-name $duration $function #{$animation-iteration-count}; 31 | -moz-animation: $animation-name $duration $function #{$animation-iteration-count}; 32 | -ms-animation: $animation-name $duration $function #{$animation-iteration-count}; 33 | } 34 | 35 | // ---------------------------------------------------------------------------- 36 | // Base styles 37 | // ---------------------------------------------------------------------------- 38 | html { 39 | font-size: 100%; 40 | -webkit-text-size-adjust: 100%; 41 | -ms-text-size-adjust: 100%; 42 | } 43 | 44 | body { 45 | margin: 0; 46 | background-color: $background-color; 47 | font-size: 20px; 48 | color: $text-color; 49 | font-family: 'Open Sans', "Helvetica Neue", Helvetica, Arial, sans-serif; 50 | } 51 | 52 | b, strong { 53 | font-weight: bold; 54 | } 55 | 56 | a { 57 | text-decoration: none; 58 | color: inherit; 59 | } 60 | 61 | img { 62 | border: 0; 63 | -ms-interpolation-mode: bicubic; 64 | vertical-align: middle; 65 | } 66 | 67 | img, object { 68 | max-width: 100%; 69 | } 70 | 71 | iframe { 72 | max-width: 100%; 73 | } 74 | 75 | table { 76 | border-collapse: collapse; 77 | border-spacing: 0; 78 | width: 100%; 79 | } 80 | 81 | td { 82 | vertical-align: middle; 83 | } 84 | 85 | ul, ol { 86 | padding: 0; 87 | margin: 0; 88 | } 89 | 90 | h1, h2, h3, h4, h5, p { 91 | padding: 0; 92 | margin: 0; 93 | } 94 | h1 { 95 | margin-bottom: 12px; 96 | text-align: center; 97 | font-size: 30px; 98 | font-weight: 400; 99 | } 100 | h2 { 101 | text-transform: uppercase; 102 | font-size: 76px; 103 | font-weight: 700; 104 | color: $text-color; 105 | } 106 | h3 { 107 | font-size: 25px; 108 | font-weight: 600; 109 | color: $text-color; 110 | } 111 | 112 | // ---------------------------------------------------------------------------- 113 | // Base widget styles 114 | // ---------------------------------------------------------------------------- 115 | .gridster { 116 | margin: 0px auto; 117 | } 118 | 119 | .icon-background { 120 | width: 100%!important; 121 | height: 100%; 122 | position: absolute; 123 | left: 0; 124 | top: 0; 125 | opacity: 0.1; 126 | font-size: 275px; 127 | text-align: center; 128 | margin-top: 82px; 129 | } 130 | 131 | .list-nostyle { 132 | list-style: none; 133 | } 134 | 135 | .gridster ul { 136 | list-style: none; 137 | } 138 | 139 | .gs_w { 140 | width: 100%; 141 | display: table; 142 | cursor: pointer; 143 | } 144 | 145 | .widget { 146 | padding: 25px 12px; 147 | text-align: center; 148 | width: 100%; 149 | display: table-cell; 150 | vertical-align: middle; 151 | } 152 | 153 | .widget.status-warning { 154 | background-color: $background-warning-color-1; 155 | @include animation(status-warning-background, 2s, ease, infinite); 156 | 157 | .icon-warning-sign { 158 | display: inline-block; 159 | } 160 | 161 | .title, .more-info { 162 | color: $text-warning-color; 163 | } 164 | } 165 | 166 | .widget.status-danger { 167 | color: $text-danger-color; 168 | background-color: $background-danger-color-1; 169 | @include animation(status-danger-background, 2s, ease, infinite); 170 | 171 | .icon-warning-sign { 172 | display: inline-block; 173 | } 174 | 175 | .title, .more-info { 176 | color: $text-danger-color; 177 | } 178 | } 179 | 180 | .more-info { 181 | font-size: 15px; 182 | position: absolute; 183 | bottom: 32px; 184 | left: 0; 185 | right: 0; 186 | } 187 | 188 | .updated-at { 189 | font-size: 15px; 190 | position: absolute; 191 | bottom: 12px; 192 | left: 0; 193 | right: 0; 194 | } 195 | 196 | #save-gridster { 197 | display: none; 198 | position: fixed; 199 | top: 0; 200 | margin: 0px auto; 201 | left: 50%; 202 | z-index: 1000; 203 | background: black; 204 | width: 190px; 205 | text-align: center; 206 | border: 1px solid white; 207 | border-top: 0px; 208 | margin-left: -95px; 209 | padding: 15px; 210 | } 211 | 212 | #save-gridster:hover { 213 | padding-top: 25px; 214 | } 215 | 216 | #saving-instructions { 217 | display: none; 218 | padding: 10px; 219 | width: 500px; 220 | height: 122px; 221 | z-index: 1000; 222 | background: white; 223 | top: 100px; 224 | color: black; 225 | font-size: 15px; 226 | padding-bottom: 4px; 227 | 228 | textarea { 229 | white-space: nowrap; 230 | width: 494px; 231 | height: 80px; 232 | } 233 | } 234 | 235 | #lean_overlay { 236 | position: fixed; 237 | z-index:100; 238 | top: 0px; 239 | left: 0px; 240 | height:100%; 241 | width:100%; 242 | background: #000; 243 | display: none; 244 | } 245 | 246 | #container { 247 | padding-top: 5px; 248 | } 249 | 250 | 251 | // ---------------------------------------------------------------------------- 252 | // Clearfix 253 | // ---------------------------------------------------------------------------- 254 | .clearfix:before, .clearfix:after { content: "\0020"; display: block; height: 0; overflow: hidden; } 255 | .clearfix:after { clear: both; } 256 | .clearfix { zoom: 1; } 257 | 258 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/assets/stylesheets/jquery.gridster.css: -------------------------------------------------------------------------------- 1 | /*! gridster.js - v0.1.0 - 2012-08-14 2 | * http://gridster.net/ 3 | * Copyright (c) 2012 ducksboard; Licensed MIT */ 4 | 5 | .gridster { 6 | position:relative; 7 | } 8 | 9 | .gridster > * { 10 | margin: 0 auto; 11 | -webkit-transition: height .4s; 12 | -moz-transition: height .4s; 13 | -o-transition: height .4s; 14 | -ms-transition: height .4s; 15 | transition: height .4s; 16 | } 17 | 18 | .gridster .gs_w{ 19 | z-index: 2; 20 | position: absolute; 21 | } 22 | 23 | .ready .gs_w:not(.preview-holder) { 24 | -webkit-transition: opacity .3s, left .3s, top .3s; 25 | -moz-transition: opacity .3s, left .3s, top .3s; 26 | -o-transition: opacity .3s, left .3s, top .3s; 27 | transition: opacity .3s, left .3s, top .3s; 28 | } 29 | 30 | .gridster .preview-holder { 31 | z-index: 1; 32 | position: absolute; 33 | background-color: #fff; 34 | border-color: #fff; 35 | opacity: 0.3; 36 | } 37 | 38 | .gridster .player-revert { 39 | z-index: 10!important; 40 | -webkit-transition: left .3s, top .3s!important; 41 | -moz-transition: left .3s, top .3s!important; 42 | -o-transition: left .3s, top .3s!important; 43 | transition: left .3s, top .3s!important; 44 | } 45 | 46 | .gridster .dragging { 47 | z-index: 10!important; 48 | -webkit-transition: all 0s !important; 49 | -moz-transition: all 0s !important; 50 | -o-transition: all 0s !important; 51 | transition: all 0s !important; 52 | } 53 | 54 | /* Uncomment this if you set helper : "clone" in draggable options */ 55 | /*.gridster .player { 56 | opacity:0; 57 | }*/ -------------------------------------------------------------------------------- /rpi-dashing/dashboard/config.ru: -------------------------------------------------------------------------------- 1 | require 'dashing' 2 | 3 | configure do 4 | set :auth_token, 'YOUR_AUTH_TOKEN' 5 | 6 | helpers do 7 | def protected! 8 | # Put any authentication code you want in here. 9 | # This method is run before accessing any resource. 10 | end 11 | end 12 | end 13 | 14 | map Sinatra::Application.assets_prefix do 15 | run Sinatra::Application.sprockets 16 | end 17 | 18 | run Sinatra::Application -------------------------------------------------------------------------------- /rpi-dashing/dashboard/dashboards/layout.erb: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | <%= yield_content(:title) %> 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 |
21 | <%= yield %> 22 |
23 | 24 | <% if development? %> 25 |
26 |

Paste the following at the top of <%= params[:dashboard] %>.erb

27 | 28 |
29 | Save this layout 30 | <% end %> 31 | 32 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/dashboards/sample.erb: -------------------------------------------------------------------------------- 1 | <% content_for :title do %>My super sweet dashboard<% end %> 2 |
3 |
    4 |
  • 5 |
    6 |
  • 7 | 8 |
  • 9 |
    10 |
  • 11 | 12 |
  • 13 |
    14 |
  • 15 | 16 |
  • 17 |
    18 |
  • 19 | 20 |
  • 21 |
    22 |
  • 23 |
24 |
Try this: curl -d '{ "auth_token": "YOUR_AUTH_TOKEN", "text": "Hey, Look what I can do!" }' \http://<%=request.host%>:<%=request.port%>/widgets/welcome
25 |
-------------------------------------------------------------------------------- /rpi-dashing/dashboard/dashboards/sampletv.erb: -------------------------------------------------------------------------------- 1 | 9 | 10 | 11 | <% content_for :title do %>1080p dashboard<% end %> 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 |
Try this: curl -d '{ "auth_token": "YOUR_AUTH_TOKEN", "text": "Hey, Look what I can do!" }' \http://<%=request.host%>:<%=request.port%>/widgets/welcome
56 |
-------------------------------------------------------------------------------- /rpi-dashing/dashboard/jobs/buzzwords.rb: -------------------------------------------------------------------------------- 1 | buzzwords = ['Paradigm shift', 'Leverage', 'Pivoting', 'Turn-key', 'Streamlininess', 'Exit strategy', 'Synergy', 'Enterprise', 'Web 2.0'] 2 | buzzword_counts = Hash.new({ value: 0 }) 3 | 4 | SCHEDULER.every '2s' do 5 | random_buzzword = buzzwords.sample 6 | buzzword_counts[random_buzzword] = { label: random_buzzword, value: (buzzword_counts[random_buzzword][:value] + 1) % 30 } 7 | 8 | send_event('buzzwords', { items: buzzword_counts.values }) 9 | end -------------------------------------------------------------------------------- /rpi-dashing/dashboard/jobs/convergence.rb: -------------------------------------------------------------------------------- 1 | # Populate the graph with some random points 2 | points = [] 3 | (1..10).each do |i| 4 | points << { x: i, y: rand(50) } 5 | end 6 | last_x = points.last[:x] 7 | 8 | SCHEDULER.every '2s' do 9 | points.shift 10 | last_x += 1 11 | points << { x: last_x, y: rand(50) } 12 | 13 | send_event('convergence', points: points) 14 | end -------------------------------------------------------------------------------- /rpi-dashing/dashboard/jobs/sample.rb: -------------------------------------------------------------------------------- 1 | current_valuation = 0 2 | current_karma = 0 3 | 4 | SCHEDULER.every '2s' do 5 | last_valuation = current_valuation 6 | last_karma = current_karma 7 | current_valuation = rand(100) 8 | current_karma = rand(200000) 9 | 10 | send_event('valuation', { current: current_valuation, last: last_valuation }) 11 | send_event('karma', { current: current_karma, last: last_karma }) 12 | send_event('synergy', { value: rand(100) }) 13 | end -------------------------------------------------------------------------------- /rpi-dashing/dashboard/jobs/twitter.rb: -------------------------------------------------------------------------------- 1 | require 'twitter' 2 | 3 | 4 | #### Get your twitter keys & secrets: 5 | #### https://dev.twitter.com/docs/auth/tokens-devtwittercom 6 | twitter = Twitter::REST::Client.new do |config| 7 | config.consumer_key = 'YOUR_CONSUMER_KEY' 8 | config.consumer_secret = 'YOUR_CONSUMER_SECRET' 9 | config.access_token = 'YOUR_OAUTH_TOKEN' 10 | config.access_token_secret = 'YOUR_OAUTH_SECRET' 11 | end 12 | 13 | search_term = URI::encode('#todayilearned') 14 | 15 | SCHEDULER.every '10m', :first_in => 0 do |job| 16 | begin 17 | tweets = twitter.search("#{search_term}") 18 | 19 | if tweets 20 | tweets = tweets.map do |tweet| 21 | { name: tweet.user.name, body: tweet.text, avatar: tweet.user.profile_image_url_https } 22 | end 23 | send_event('twitter_mentions', comments: tweets) 24 | end 25 | rescue Twitter::Error 26 | puts "\e[33mFor the twitter widget to work, you need to put in your twitter API keys in the jobs/twitter.rb file.\e[0m" 27 | end 28 | end -------------------------------------------------------------------------------- /rpi-dashing/dashboard/public/404.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | This Dashboard doesn't exist. 5 | 17 | 18 | 19 | 20 | 21 |
22 |

Drats! That Dashboard doesn't exist.

23 |

You may have mistyped the address or the page may have moved.

24 |
25 | 26 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-dashing/dashboard/public/favicon.ico -------------------------------------------------------------------------------- /rpi-dashing/dashboard/start.sh: -------------------------------------------------------------------------------- 1 | bundle 2 | dashing start -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/clock/clock.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Clock extends Dashing.Widget 2 | 3 | ready: -> 4 | setInterval(@startTime, 500) 5 | 6 | startTime: => 7 | today = new Date() 8 | 9 | h = today.getHours() 10 | m = today.getMinutes() 11 | s = today.getSeconds() 12 | m = @formatTime(m) 13 | s = @formatTime(s) 14 | @set('time', h + ":" + m + ":" + s) 15 | @set('date', today.toDateString()) 16 | 17 | formatTime: (i) -> 18 | if i < 10 then "0" + i else i -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/clock/clock.html: -------------------------------------------------------------------------------- 1 |

2 |

-------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/clock/clock.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #dc5945; 5 | 6 | // ---------------------------------------------------------------------------- 7 | // Widget-clock styles 8 | // ---------------------------------------------------------------------------- 9 | .widget-clock { 10 | 11 | background-color: $background-color; 12 | 13 | } 14 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/comments/comments.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Comments extends Dashing.Widget 2 | 3 | @accessor 'quote', -> 4 | "“#{@get('current_comment')?.body}”" 5 | 6 | ready: -> 7 | @currentIndex = 0 8 | @commentElem = $(@node).find('.comment-container') 9 | @nextComment() 10 | @startCarousel() 11 | 12 | onData: (data) -> 13 | @currentIndex = 0 14 | 15 | startCarousel: -> 16 | setInterval(@nextComment, 8000) 17 | 18 | nextComment: => 19 | comments = @get('comments') 20 | if comments 21 | @commentElem.fadeOut => 22 | @currentIndex = (@currentIndex + 1) % comments.length 23 | @set 'current_comment', comments[@currentIndex] 24 | @commentElem.fadeIn() 25 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/comments/comments.html: -------------------------------------------------------------------------------- 1 |

2 |
3 |

4 |

5 |
6 | 7 |

8 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/comments/comments.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #eb9c3c; 5 | 6 | $title-color: rgba(255, 255, 255, 0.7); 7 | $moreinfo-color: rgba(255, 255, 255, 0.7); 8 | 9 | // ---------------------------------------------------------------------------- 10 | // Widget-comment styles 11 | // ---------------------------------------------------------------------------- 12 | .widget-comments { 13 | 14 | background-color: $background-color; 15 | 16 | .title { 17 | color: $title-color; 18 | margin-bottom: 15px; 19 | } 20 | 21 | .name { 22 | padding-left: 5px; 23 | } 24 | 25 | .comment-container { 26 | display: none; 27 | } 28 | 29 | .more-info { 30 | color: $moreinfo-color; 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/graph/graph.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Graph extends Dashing.Widget 2 | 3 | @accessor 'current', -> 4 | return @get('displayedValue') if @get('displayedValue') 5 | points = @get('points') 6 | if points 7 | points[points.length - 1].y 8 | 9 | ready: -> 10 | container = $(@node).parent() 11 | # Gross hacks. Let's fix this. 12 | width = (Dashing.widget_base_dimensions[0] * container.data("sizex")) + Dashing.widget_margins[0] * 2 * (container.data("sizex") - 1) 13 | height = (Dashing.widget_base_dimensions[1] * container.data("sizey")) 14 | @graph = new Rickshaw.Graph( 15 | element: @node 16 | width: width 17 | height: height 18 | renderer: @get("graphtype") 19 | series: [ 20 | { 21 | color: "#fff", 22 | data: [{x:0, y:0}] 23 | } 24 | ] 25 | ) 26 | 27 | @graph.series[0].data = @get('points') if @get('points') 28 | 29 | x_axis = new Rickshaw.Graph.Axis.Time(graph: @graph) 30 | y_axis = new Rickshaw.Graph.Axis.Y(graph: @graph, tickFormat: Rickshaw.Fixtures.Number.formatKMBT) 31 | @graph.render() 32 | 33 | onData: (data) -> 34 | if @graph 35 | @graph.series[0].data = data.points 36 | @graph.render() 37 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/graph/graph.html: -------------------------------------------------------------------------------- 1 |

2 | 3 |

4 | 5 |

6 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/graph/graph.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #dc5945; 5 | 6 | $title-color: rgba(255, 255, 255, 0.7); 7 | $moreinfo-color: rgba(255, 255, 255, 0.3); 8 | $tick-color: rgba(0, 0, 0, 0.4); 9 | 10 | 11 | // ---------------------------------------------------------------------------- 12 | // Widget-graph styles 13 | // ---------------------------------------------------------------------------- 14 | .widget-graph { 15 | 16 | background-color: $background-color; 17 | position: relative; 18 | 19 | 20 | svg { 21 | position: absolute; 22 | opacity: 0.4; 23 | fill-opacity: 0.4; 24 | left: 0px; 25 | top: 0px; 26 | } 27 | 28 | .title, .value { 29 | position: relative; 30 | z-index: 99; 31 | } 32 | 33 | .title { 34 | color: $title-color; 35 | } 36 | 37 | .more-info { 38 | color: $moreinfo-color; 39 | font-weight: 600; 40 | font-size: 20px; 41 | margin-top: 0; 42 | } 43 | 44 | .x_tick { 45 | position: absolute; 46 | bottom: 0; 47 | .title { 48 | font-size: 20px; 49 | color: $tick-color; 50 | opacity: 0.5; 51 | padding-bottom: 3px; 52 | } 53 | } 54 | 55 | .y_ticks { 56 | font-size: 20px; 57 | fill: $tick-color; 58 | fill-opacity: 1; 59 | } 60 | 61 | .domain { 62 | display: none; 63 | } 64 | 65 | } 66 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/iframe/iframe.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Iframe extends Dashing.Widget 2 | 3 | ready: -> 4 | # This is fired when the widget is done being rendered 5 | 6 | onData: (data) -> 7 | # Handle incoming data 8 | # You can access the html node of this widget with `@node` 9 | # Example: $(@node).fadeOut().fadeIn() will make the node flash each time data comes in. 10 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/iframe/iframe.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/iframe/iframe.scss: -------------------------------------------------------------------------------- 1 | .widget-iframe { 2 | padding: 3px 0px 0px 0px !important; 3 | 4 | iframe { 5 | width: 100%; 6 | height: 100%; 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/image/image.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Image extends Dashing.Widget 2 | 3 | ready: -> 4 | # This is fired when the widget is done being rendered 5 | 6 | onData: (data) -> 7 | # Handle incoming data 8 | # You can access the html node of this widget with `@node` 9 | # Example: $(@node).fadeOut().fadeIn() will make the node flash each time data comes in. 10 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/image/image.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/image/image.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #4b4b4b; 5 | 6 | // ---------------------------------------------------------------------------- 7 | // Widget-image styles 8 | // ---------------------------------------------------------------------------- 9 | .widget-image { 10 | 11 | background-color: $background-color; 12 | 13 | } 14 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/list/list.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.List extends Dashing.Widget 2 | ready: -> 3 | if @get('unordered') 4 | $(@node).find('ol').remove() 5 | else 6 | $(@node).find('ul').remove() 7 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/list/list.html: -------------------------------------------------------------------------------- 1 |

2 | 3 |
    4 |
  1. 5 | 6 | 7 |
  2. 8 |
9 | 10 |
    11 |
  • 12 | 13 | 14 |
  • 15 |
16 | 17 |

18 |

19 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/list/list.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #12b0c5; 5 | $value-color: #fff; 6 | 7 | $title-color: rgba(255, 255, 255, 0.7); 8 | $label-color: rgba(255, 255, 255, 0.7); 9 | $moreinfo-color: rgba(255, 255, 255, 0.7); 10 | 11 | // ---------------------------------------------------------------------------- 12 | // Widget-list styles 13 | // ---------------------------------------------------------------------------- 14 | .widget-list { 15 | 16 | background-color: $background-color; 17 | vertical-align: top; 18 | 19 | .title { 20 | color: $title-color; 21 | } 22 | 23 | ol, ul { 24 | margin: 0 15px; 25 | text-align: left; 26 | color: $label-color; 27 | } 28 | 29 | ol { 30 | list-style-position: inside; 31 | } 32 | 33 | li { 34 | margin-bottom: 5px; 35 | } 36 | 37 | .list-nostyle { 38 | list-style: none; 39 | } 40 | 41 | .label { 42 | color: $label-color; 43 | } 44 | 45 | .value { 46 | float: right; 47 | margin-left: 12px; 48 | font-weight: 600; 49 | color: $value-color; 50 | } 51 | 52 | .updated-at { 53 | color: rgba(0, 0, 0, 0.3); 54 | } 55 | 56 | .more-info { 57 | color: $moreinfo-color; 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/meter/meter.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Meter extends Dashing.Widget 2 | 3 | @accessor 'value', Dashing.AnimatedValue 4 | 5 | constructor: -> 6 | super 7 | @observe 'value', (value) -> 8 | $(@node).find(".meter").val(value).trigger('change') 9 | 10 | ready: -> 11 | meter = $(@node).find(".meter") 12 | meter.attr("data-bgcolor", meter.css("background-color")) 13 | meter.attr("data-fgcolor", meter.css("color")) 14 | meter.knob() 15 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/meter/meter.html: -------------------------------------------------------------------------------- 1 |

2 | 3 | 4 | 5 |

6 | 7 |

8 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/meter/meter.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #9c4274; 5 | 6 | $title-color: rgba(255, 255, 255, 0.7); 7 | $moreinfo-color: rgba(255, 255, 255, 0.3); 8 | 9 | $meter-background: darken($background-color, 15%); 10 | 11 | // ---------------------------------------------------------------------------- 12 | // Widget-meter styles 13 | // ---------------------------------------------------------------------------- 14 | .widget-meter { 15 | 16 | background-color: $background-color; 17 | 18 | input.meter { 19 | background-color: $meter-background; 20 | color: #fff; 21 | } 22 | 23 | .title { 24 | color: $title-color; 25 | } 26 | 27 | .more-info { 28 | color: $moreinfo-color; 29 | } 30 | 31 | .updated-at { 32 | color: rgba(0, 0, 0, 0.3); 33 | } 34 | 35 | } 36 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/number/number.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Number extends Dashing.Widget 2 | @accessor 'current', Dashing.AnimatedValue 3 | 4 | @accessor 'difference', -> 5 | if @get('last') 6 | last = parseInt(@get('last')) 7 | current = parseInt(@get('current')) 8 | if last != 0 9 | diff = Math.abs(Math.round((current - last) / last * 100)) 10 | "#{diff}%" 11 | else 12 | "" 13 | 14 | @accessor 'arrow', -> 15 | if @get('last') 16 | if parseInt(@get('current')) > parseInt(@get('last')) then 'icon-arrow-up' else 'icon-arrow-down' 17 | 18 | onData: (data) -> 19 | if data.status 20 | # clear existing "status-*" classes 21 | $(@get('node')).attr 'class', (i,c) -> 22 | c.replace /\bstatus-\S+/g, '' 23 | # add new class 24 | $(@get('node')).addClass "status-#{data.status}" 25 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/number/number.html: -------------------------------------------------------------------------------- 1 |

2 | 3 |

4 | 5 |

6 | 7 |

8 | 9 |

10 | 11 |

12 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/number/number.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #47bbb3; 5 | $value-color: #fff; 6 | 7 | $title-color: rgba(255, 255, 255, 0.7); 8 | $moreinfo-color: rgba(255, 255, 255, 0.7); 9 | 10 | // ---------------------------------------------------------------------------- 11 | // Widget-number styles 12 | // ---------------------------------------------------------------------------- 13 | .widget-number { 14 | 15 | background-color: $background-color; 16 | 17 | .title { 18 | color: $title-color; 19 | } 20 | 21 | .value { 22 | color: $value-color; 23 | } 24 | 25 | .change-rate { 26 | font-weight: 500; 27 | font-size: 30px; 28 | color: $value-color; 29 | } 30 | 31 | .more-info { 32 | color: $moreinfo-color; 33 | } 34 | 35 | .updated-at { 36 | color: rgba(0, 0, 0, 0.3); 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/text/text.coffee: -------------------------------------------------------------------------------- 1 | class Dashing.Text extends Dashing.Widget 2 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/text/text.html: -------------------------------------------------------------------------------- 1 |

2 | 3 |

4 | 5 |

6 | 7 |

8 | -------------------------------------------------------------------------------- /rpi-dashing/dashboard/widgets/text/text.scss: -------------------------------------------------------------------------------- 1 | // ---------------------------------------------------------------------------- 2 | // Sass declarations 3 | // ---------------------------------------------------------------------------- 4 | $background-color: #ec663c; 5 | 6 | $title-color: rgba(255, 255, 255, 0.7); 7 | $moreinfo-color: rgba(255, 255, 255, 0.7); 8 | 9 | // ---------------------------------------------------------------------------- 10 | // Widget-text styles 11 | // ---------------------------------------------------------------------------- 12 | .widget-text { 13 | 14 | background-color: $background-color; 15 | 16 | .title { 17 | color: $title-color; 18 | } 19 | 20 | .more-info { 21 | color: $moreinfo-color; 22 | } 23 | 24 | .updated-at { 25 | color: rgba(255, 255, 255, 0.7); 26 | } 27 | 28 | 29 | &.large h3 { 30 | font-size: 65px; 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /rpi-dnsmasq/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | dnsmasq \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | ADD dnsmasq.conf /etc/dnsmasq.conf 11 | 12 | EXPOSE 67 13 | 14 | ENTRYPOINT ["dnsmasq","-d"] 15 | -------------------------------------------------------------------------------- /rpi-dnsmasq/dnsmasq.conf: -------------------------------------------------------------------------------- 1 | interface=eth0 2 | dhcp-range=192.168.2.2,192.168.2.254,255.255.255.0,12h 3 | -------------------------------------------------------------------------------- /rpi-dump1090/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | pkg-config \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | RUN git clone git://github.com/antirez/dump1090.git && \ 12 | cd dump1090 && \ 13 | make 14 | 15 | USER root 16 | 17 | ENTRYPOINT ["/dump1090/dump1090", "--interactive", "--net"] 18 | -------------------------------------------------------------------------------- /rpi-epiphany/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | epiphany-browser \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | ENTRYPOINT ["epiphany-browser"] 11 | -------------------------------------------------------------------------------- /rpi-errbot/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | ENV ERR_USER err 4 | ENV DEBIAN_FRONTEND noninteractive 5 | ENV PATH /app/venv/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin 6 | 7 | ENV LC_ALL C.UTF-8 8 | ENV LANG en_US.UTF-8 9 | ENV LANGUAGE en_US.UTF-8 10 | 11 | RUN groupadd -r $ERR_USER && \ 12 | useradd -r \ 13 | -g $ERR_USER \ 14 | -d /srv \ 15 | $ERR_USER 16 | 17 | RUN apt-get update && apt-get install -y -q \ 18 | git \ 19 | locales \ 20 | dnsutils \ 21 | python3-dnspython \ 22 | python3-openssl \ 23 | python3-pip \ 24 | python3-cffi \ 25 | python3-pyasn1 \ 26 | --no-install-recommends && \ 27 | rm -rf /var/lib/apt-lists/* 28 | 29 | RUN locale-gen C.UTF-8 && \ 30 | /usr/sbin/update-locale LANG=C.UTF-8 && \ 31 | echo 'en_US.UTF-8 UTF-8' >> /etc/locale.gen && \ 32 | locale-gen 33 | 34 | RUN pip3 install virtualenv && \ 35 | rm -rf /var/lib/apt/lists/* 36 | 37 | RUN mkdir /srv/data /srv/plugins /srv/errbackends /app && \ 38 | chown -R $ERR_USER: /srv /app 39 | 40 | USER $ERR_USER 41 | WORKDIR /srv 42 | 43 | COPY requirements.txt /app/requirements.txt 44 | 45 | RUN virtualenv --system-site-packages -p python3 /app/venv 46 | RUN /app/venv/bin/pip3 install --no-cache-dir -r /app/requirements.txt 47 | 48 | COPY config.py /app/config.py 49 | COPY run.sh /app/venv/bin/run.sh 50 | 51 | EXPOSE 3141 3142 52 | VOLUME ["/srv"] 53 | 54 | CMD ["/app/venv/bin/run.sh"] 55 | -------------------------------------------------------------------------------- /rpi-errbot/config.py: -------------------------------------------------------------------------------- 1 | ########################################################################## 2 | # # 3 | # This is the config-template for Err. This file should be copied and # 4 | # renamed to config.py, then modified as you see fit to run Err the way # 5 | # you like it. # 6 | # # 7 | # As this is a regular Python file, note that you can do variable # 8 | # assignments and the likes as usual. This can be useful for example if # 9 | # you use the same values in multiple places. # 10 | # # 11 | # Note: Various config options require a tuple to be specified, even # 12 | # when you are configuring only a single value. An example of this is # 13 | # the BOT_ADMINS option. Make sure you use a valid tuple here, even if # 14 | # you are only configuring a single item, else you will get errors. # 15 | # (So don't forget the trailing ',' in these cases) # 16 | # # 17 | ########################################################################## 18 | 19 | import os 20 | import logging 21 | 22 | ########################################################################## 23 | # Core Err configuration # 24 | ########################################################################## 25 | 26 | # BACKEND selection. 27 | # This configures the type of chat server you which to use Err with. 28 | # 29 | # The current choices: 30 | 31 | # Debug backends to test your plugins manually: 32 | # 'Text' - on the text console 33 | # 'Graphic' - in a GUI window 34 | 35 | # Commercial backends: 36 | # 'Campfire' - see https://campfirenow.com/ 37 | # 'Hipchat' - see https://www.hipchat.com/ 38 | # 'Slack' - see https://slack.com/ 39 | 40 | # Open protocols: 41 | # 'TOX' - see https://tox.im/ 42 | # 'IRC' - for classic IRC or bridged services like https://gitter.im 43 | # 'XMPP' 44 | 45 | BACKEND = os.environ.get('BACKEND', 'XMPP') 46 | 47 | # The location where all of Err's data should be stored. Make sure to set 48 | # this to a directory that is writable by the user running the bot. 49 | BOT_DATA_DIR = '/srv/data' 50 | 51 | # Set this to a directory on your system where you want to load extra 52 | # plugins from, which is useful mostly if you want to develop a plugin 53 | # locally before publishing it. Note that you can specify only a single 54 | # directory, however you are free to create subdirectories with multiple 55 | # plugins inside this directory. 56 | BOT_EXTRA_PLUGIN_DIR = '/srv/plugins' 57 | 58 | # If you use an external backend as a plugin, 59 | # this is where you tell err where to find it. 60 | BOT_EXTRA_BACKEND_DIR = '/srv/errbackends' 61 | 62 | # Should plugin dependencies be installed automatically? If this is true 63 | # then Err will use pip to install any missing dependencies automatically. 64 | # 65 | # If you have installed Err in a virtualenv, this will run the equivalent 66 | # of `pip install -r requirements.txt`. 67 | # If no virtualenv is detected, the equivalent of `pip install --user -r 68 | # requirements.txt` is used to ensure the package(s) is/are only installed for 69 | # the user running Err. 70 | AUTOINSTALL_DEPS = True 71 | 72 | # The location of the log file. If you set this to None, then logging will 73 | # happen to console only. 74 | BOT_LOG_FILE = '/srv/err.log' 75 | 76 | # The verbosity level of logging that is done to the above logfile, and to 77 | # the console. This takes the standard Python logging levels, DEBUG, INFO, 78 | # WARN, ERROR. For more info, see http://docs.python.org/library/logging.html 79 | # 80 | # If you encounter any issues with Err, please set your log level to 81 | # logging.DEBUG and attach a log with your bug report to aid the developers 82 | # in debugging the issue. 83 | BOT_LOG_LEVEL = logging.getLevelName(os.environ.get('BOT_LOG_LEVEL', 'INFO')) 84 | 85 | # Enable logging to sentry (find out more about sentry at www.getsentry.com). 86 | # This is optional and disabled by default. 87 | BOT_LOG_SENTRY = False 88 | SENTRY_DSN = '' 89 | SENTRY_LOGLEVEL = BOT_LOG_LEVEL 90 | 91 | # Execute commands in asynchronous mode. In this mode, Err will spawn 3 92 | # seperate threads to handle commands, instead of blocking on each 93 | # single command. 94 | BOT_ASYNC = True 95 | 96 | ########################################################################## 97 | # Account and chatroom (MUC) configuration # 98 | ########################################################################## 99 | 100 | BOT_IDENTITY = {} 101 | 102 | # username 103 | if 'BOT_USERNAME' in os.environ: 104 | BOT_IDENTITY['username'] = os.environ['BOT_USERNAME'] 105 | 106 | # password 107 | if 'BOT_PASSWORD' in os.environ: 108 | BOT_IDENTITY['password'] = os.environ['BOT_PASSWORD'] 109 | 110 | # server 111 | if 'BOT_SERVER' in os.environ: 112 | if ':' in os.environ['BOT_SERVER']: 113 | server, port = os.environ['BOT_SERVER'].split(':') 114 | BOT_IDENTITY['server'] = (server, int(port)) 115 | else: 116 | BOT_IDENTITY['server'] = os.environ['BOT_SERVER'] 117 | 118 | # token 119 | if 'BOT_TOKEN' in os.environ: 120 | BOT_IDENTITY['token'] = os.environ['BOT_TOKEN'] 121 | 122 | # endpoint 123 | if 'BOT_ENDPOINT' in os.environ: 124 | BOT_IDENTITY['endpoint'] = os.environ['BOT_ENDPOINT'] 125 | 126 | # nickname 127 | if 'BOT_NICKNAME' in os.environ: 128 | BOT_IDENTITY['nickname'] = os.environ['BOT_NICKNAME'] 129 | 130 | # port 131 | if 'BOT_PORT' in os.environ: 132 | BOT_IDENTITY['port'] = os.environ['BOT_PORT'] 133 | 134 | # ssl 135 | if 'BOT_SSL' in os.environ: 136 | BOT_IDENTITY['ssl'] = os.environ['BOT_SSL'] 137 | 138 | # The identity, or credentials, used to connect to a server 139 | # BOT_IDENTITY = { 140 | # XMPP (Jabber) mode 141 | # 'username': 'err@localhost', # The JID of the user you have created for the bot 142 | # 'password': 'changeme', # The corresponding password for this user 143 | # 'server': ('host.domain.tld',5222), # server override 144 | 145 | ## HipChat mode (Comment the above if using this mode) 146 | # 'username' : '12345_123456@chat.hipchat.com', 147 | # 'password' : 'changeme', 148 | ## Group admins can create/view tokens on the settings page after logging 149 | ## in on HipChat's website 150 | # 'token' : 'ed4b74d62833267d98aa99f312ff04', 151 | ## If you're using HipChat server (self-hosted HipChat) then you should set 152 | ## the endpoint below. If you don't use HipChat server but use the hosted version 153 | ## of HipChat then you may leave this commented out. 154 | # 'endpoint' : 'https://api.hipchat.com' 155 | 156 | ## Slack Mode (comment the others above if using this mode) 157 | # 'token': 'xoxb-4426949411-aEM7...', 158 | 159 | ## IRC mode (Comment the others above if using this mode) 160 | # 'nickname' : 'err-chatbot', 161 | # 'username' : 'err-chatbot', # optional, defaults to nickname if omitted 162 | # 'password' : None, # optional 163 | # 'server' : 'irc.freenode.net', 164 | # 'port': 6667, # optional 165 | # 'ssl': False, # optional 166 | # } 167 | 168 | ## TOX Mode 169 | # TOX_BOOTSTRAP_SERVER = ["54.199.139.199", 33445, "7F9C31FE850E97CEFD4C4591DF93FC757C7C12549DDD55F8EEAECC34FE76C029"] 170 | 171 | # Set the admins of your bot. Only these users will have access 172 | # to the admin-only commands. 173 | # 174 | # Campfire syntax is the full name: 175 | # BOT_ADMINS = ('Guillaume Binet',) 176 | # 177 | # TOX syntax is a hash. 178 | # BOT_ADMINS = ['F9886B47503FB80E6347CC0907D8000144305796DE54693253AA5E574E5E8106C7D002557189', ] 179 | BOT_ADMINS = tuple( 180 | os.environ.get('BOT_ADMINS', 'admin@localhost').split(','), 181 | ) 182 | # Chatrooms your bot should join on startup. For the IRC backend you 183 | # should include the # sign here. For XMPP rooms that are password 184 | # protected, you can specify another tuple here instead of a string, 185 | # using the format (RoomName, Password). 186 | CHATROOM_PRESENCE = tuple( 187 | os.environ.get('CHATROOM_PRESENCE', 188 | 'err@conference.localhost').split(','), 189 | ) 190 | # The FullName, or nickname, your bot should use. What you set here will 191 | # be the nickname that Err shows in chatrooms. Note that some XMPP 192 | # implementations, notably HipChat, are very picky about what name you 193 | # use. In the case of HipChat, make sure this matches exactly with the 194 | # name you gave the user. 195 | CHATROOM_FN = os.environ.get('CHATROOM_FN', 'Err') 196 | 197 | ########################################################################## 198 | # Prefix configuration # 199 | ########################################################################## 200 | 201 | # Command prefix, the prefix that is expected in front of commands directed 202 | # at the bot. 203 | # 204 | # Note: When writing plugins,you should always use the default '!'. 205 | # If the prefix is changed from the default, the help strings will be 206 | # automatically adjusted for you. 207 | # 208 | BOT_PREFIX = os.environ.get('BOT_PREFIX', '!') 209 | 210 | # Uncomment the following and set it to True if you want the prefix to be 211 | # optional for normal chat. 212 | # (Meaning messages sent directly to the bot as opposed to within a MUC) 213 | #BOT_PREFIX_OPTIONAL_ON_CHAT = False 214 | BOT_PREFIX_OPTIONAL_ON_CHAT = bool( 215 | os.environ.get('BOT_PREFIX_OPTIONAL_ON_CHAT', False) 216 | ) 217 | 218 | # You might wish to have your bot respond by being called with certain 219 | # names, rather than the BOT_PREFIX above. This option allows you to 220 | # specify alternative prefixes the bot will respond to in addition to 221 | # the prefix above. 222 | #BOT_ALT_PREFIXES = ('Err',) 223 | BOT_ALT_PREFIXES = tuple( 224 | os.environ.get('BOT_ALT_PREFIXES', 'Err').split(','), 225 | ) 226 | 227 | # If you use alternative prefixes, you might want to allow users to insert 228 | # separators like , and ; between the prefix and the command itself. This 229 | # allows users to refer to your bot like this (Assuming 'Err' is in your 230 | # BOT_ALT_PREFIXES): 231 | # "Err, status" or "Err: status" 232 | # 233 | # Note: There's no need to add spaces to the separators here 234 | # 235 | #BOT_ALT_PREFIX_SEPARATORS = (':', ',', ';') 236 | BOT_ALT_PREFIX_SEPARATORS = tuple( 237 | os.environ.get('BOT_ALT_PREFIX_SEPARATORS', ': , ;').split(' '), 238 | ) 239 | 240 | # Continuing on this theme, you might want to permit your users to be 241 | # lazy and not require correct capitalization, so they can do 'Err', 242 | # 'err' or even 'ERR'. 243 | #BOT_ALT_PREFIX_CASEINSENSITIVE = True 244 | BOT_ALT_PREFIX_CASEINSENSITIVE = bool( 245 | os.environ.get('BOT_ALT_PREFIX_CASEINSENSITIVE', False) 246 | ) 247 | 248 | ########################################################################## 249 | # Access controls and message diversion # 250 | ########################################################################## 251 | 252 | # Access controls, allowing commands to be restricted to specific users/rooms. 253 | # Available filters (you can omit a filter or set it to None to disable it): 254 | # allowusers: Allow command from these users only 255 | # denyusers: Deny command from these users 256 | # allowrooms: Allow command only in these rooms (and direct messages) 257 | # denyrooms: Deny command in these rooms 258 | # allowprivate: Allow command from direct messages to the bot 259 | # allowmuc: Allow command inside rooms 260 | # Rules listed in ACCESS_CONTROLS_DEFAULT are applied when a command cannot 261 | # be found inside ACCESS_CONTROLS 262 | # 263 | # Example: 264 | #ACCESS_CONTROLS_DEFAULT = {} # Allow everyone access by default 265 | #ACCESS_CONTROLS = {'status': {'allowrooms': ('someroom@conference.localhost',)}, 266 | # 'about': {'denyusers': ('baduser@localhost',), 'allowrooms': ('room1@conference.localhost', 'room2@conference.localhost')}, 267 | # 'uptime': {'allowusers': BOT_ADMINS}, 268 | # 'help': {'allowmuc': False}, 269 | # } 270 | 271 | # Uncomment and set this to True to hide the restricted commands from 272 | # the help output. 273 | #HIDE_RESTRICTED_COMMANDS = False 274 | HIDE_RESTRICTED_COMMANDS = bool( 275 | os.environ.get('HIDE_RESTRICTED_COMMANDS', False) 276 | ) 277 | 278 | # Uncomment and set this to True to ignore commands from users that have no 279 | # access for these instead of replying with error message. 280 | #HIDE_RESTRICTED_ACCESS = False 281 | HIDE_RESTRICTED_ACCESS = bool( 282 | os.environ.get('HIDE_RESTRICTED_ACCESS', False) 283 | ) 284 | 285 | # A list of commands which should be responded to in private, even if 286 | # the command was given in a MUC. For example: 287 | # DIVERT_TO_PRIVATE = ('help', 'about', 'status') 288 | #DIVERT_TO_PRIVATE = () 289 | DIVERT_TO_PRIVATE = tuple( 290 | os.environ.get('DIVERT_TO_PRIVATE', '').split(','), 291 | ) 292 | 293 | # Chat relay 294 | # Can be used to relay one to one message from specific users to the bot 295 | # to MUCs. This can be useful with XMPP notifiers like for example the 296 | # standard Altassian Jira which don't have native support for MUC. 297 | # For example: CHATROOM_RELAY = {'gbin@localhost' : (_TEST_ROOM,)} 298 | CHATROOM_RELAY = {} 299 | 300 | # Reverse chat relay 301 | # This feature forwards whatever is said to a specific user. 302 | # It can be useful if you client like gtalk doesn't support MUC correctly 303 | # For example: REVERSE_CHATROOM_RELAY = {_TEST_ROOM : ('gbin@localhost',)} 304 | REVERSE_CHATROOM_RELAY = {} 305 | 306 | ########################################################################## 307 | # Miscellaneous configuration options # 308 | ########################################################################## 309 | 310 | # Define the maximum length a single message may be. If a plugin tries to 311 | # send a message longer than this length, it will be broken up into multiple 312 | # shorter messages that do fit. 313 | #MESSAGE_SIZE_LIMIT = 10000 314 | MESSAGE_SIZE_LIMIT = int(os.environ.get('MESSAGE_SIZE_LIMIT', 10000)) 315 | 316 | # XMPP TLS certificate verification. In order to validate offered certificates, 317 | # you must supply a path to a file containing certificate authorities. By 318 | # default, "/etc/ssl/certs/ca-certificates.crt" is used, which on most Linux 319 | # systems holds the default system trusted CA certificates. You might need to 320 | # change this depending on your environment. Setting this to None disables 321 | # certificate validation, which can be useful if you have a self-signed 322 | # certificate for example. 323 | XMPP_CA_CERT_FILE = None 324 | if 'XMPP_CA_CERT_FILE' in os.environ: 325 | if 'default' == os.environ['XMPP_CA_CERT_FILE'].lower(): 326 | XMPP_CA_CERT_FILE = '/etc/ssl/certs/ca-certificates.crt' 327 | else: 328 | XMPP_CA_CERT_FILE = os.environ['XMPP_CA_CERT_FILE'] 329 | 330 | # Influence the security methods used on connection with XMPP-based 331 | # backends. You can use this to work around authentication issues with 332 | # some buggy XMPP servers. 333 | # 334 | # The default is to try anything: 335 | #XMPP_FEATURE_MECHANISMS = {} 336 | # To use only unencrypted plain auth: 337 | #XMPP_FEATURE_MECHANISMS = {'use_mech': 'PLAIN', 'unencrypted_plain': True, 'encrypted_plain': False} 338 | 339 | # Modify the default keep-alive interval. By default, Err will send 340 | # some whitespace to the XMPP server every 300 seconds to keep the TCP 341 | # connection alive. On some servers, or when running Err from behind 342 | # a NAT router, the default might not be fast enough and you will need 343 | # to set it to a lower value. 344 | # 345 | # It has been reported that HipChat also times out without setting this 346 | # to a lower value (60 seems to work well with HipChat) 347 | # 348 | # If you're having issues with your bot getting constantly disconnected, 349 | # try to gradually lower this value until it no longer happens. 350 | #XMPP_KEEPALIVE_INTERVAL = 300 351 | 352 | # Message rate limiting for the IRC backend. This will delay subsequent 353 | # messages by this many seconds (floats are supported). Setting these 354 | # to a value of 0 effectively disables rate limiting. 355 | #IRC_CHANNEL_RATE = 1 # Regular channel messages 356 | #IRC_PRIVATE_RATE = 1 # Private messages 357 | 358 | # Allow messages sent in a chatroom to be directed at requester. 359 | #GROUPCHAT_NICK_PREFIXED = False 360 | -------------------------------------------------------------------------------- /rpi-errbot/requirements.txt: -------------------------------------------------------------------------------- 1 | errbot==3.2.4 2 | sleekxmpp 3 | pyasn1-modules 4 | irc 5 | hypchat 6 | slackclient 7 | -------------------------------------------------------------------------------- /rpi-errbot/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e 3 | 4 | readonly ERRBIN="/app/venv/bin/errbot" 5 | readonly ERRRUN="/srv" 6 | 7 | 8 | is_set() { 9 | local var=$1 10 | 11 | [[ -n $var ]] 12 | } 13 | 14 | 15 | file_exist() { 16 | local file=$1 17 | 18 | [[ -e $file ]] 19 | } 20 | 21 | 22 | # if mounted volume is empty create dirs 23 | if [ ! "$(ls -A ${ERRRUN})" ]; then 24 | mkdir "${ERRRUN}/data" "${ERRRUN}/plugins" "${ERRRUN}/errbackends" 25 | fi 26 | 27 | 28 | # copy default container image config file if not exist on volume 29 | file_exist ${ERRCONF} \ 30 | || cp /app/config.py ${ERRRUN} 31 | 32 | 33 | # sleep if we need to wait for another container 34 | if ( is_set ${WAIT} ); then 35 | echo "Sleep ${WAIT} seconds before starting err..." 36 | sleep ${WAIT} 37 | fi 38 | 39 | 40 | exec ${ERRBIN} $@ 41 | -------------------------------------------------------------------------------- /rpi-festival/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | festival \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | CMD ["echo", "'this is a text to speech test'", "|", "festival", "--tts"] 11 | -------------------------------------------------------------------------------- /rpi-flite/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | flite \ 7 | --no-install-recommends \ 8 | && rm -rf /var/lib/apt/lists/* 9 | 10 | CMD ["flite", "-t", "'this is a text to speech test'"] 11 | -------------------------------------------------------------------------------- /rpi-freqshow/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | python-pygame \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN git clone git://github.com/adafruit/FreqShow.git 11 | 12 | WORKDIR FreqShow 13 | 14 | USER root 15 | 16 | ENTRYPOINT ["python", "freqshow.py"] 17 | -------------------------------------------------------------------------------- /rpi-glances/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | gcc \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN pip install bottle \ 11 | docker-py \ 12 | glances \ 13 | netifaces \ 14 | psutil \ 15 | statsd 16 | 17 | EXPOSE 61208 18 | 19 | #CMD ["glances", "-w"] 20 | CMD ["glances"] 21 | -------------------------------------------------------------------------------- /rpi-gnuradio/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | gnuradio \ 7 | gnuradio-dev \ 8 | gr-osmosdr \ 9 | --no-install-recommends && \ 10 | rm -rf /var/lib/apt/lists/* 11 | 12 | ENTRYPOINT ["osmocom_fft"] 13 | 14 | -------------------------------------------------------------------------------- /rpi-gpio-gmail/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-gpio-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN pip install feedparser 6 | 7 | COPY ./gpio_gmail.py /bin/gpio_gmail.py 8 | 9 | VOLUME ["/data"] 10 | 11 | WORKDIR /data 12 | -------------------------------------------------------------------------------- /rpi-gpio-gmail/gpio_gmail.py: -------------------------------------------------------------------------------- 1 | import RPi.GPIO as GPIO, feedparser 2 | USERNAME="username@gmail.com" 3 | PASSWORD="password" 4 | GPIO_PIN=12 5 | GPIO.setmode(GPIO.BOARD) 6 | GPIO.setup(GPIO_PIN, GPIO.OUT) 7 | newmails = int(feedparser.parse("https://" + USERNAME + ":" + PASSWORD + "@mail.google.com/gmail/feed/atom")["feed"]["fullcount"]) 8 | if newmails > 0: 9 | GPIO.output(GPIO_PIN, True) 10 | else: 11 | GPIO.output(GPIO_PIN, False) 12 | -------------------------------------------------------------------------------- /rpi-gpio-python/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | gcc \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN pip install RPi.GPIO 11 | 12 | WORKDIR /data 13 | 14 | CMD ["bash"] 15 | -------------------------------------------------------------------------------- /rpi-gtalk-robot/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-gpio-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | git-core \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN pip install xmpppy pydns 11 | 12 | RUN git clone git://github.com/mitchtech/raspi_gtalk_robot.git 13 | 14 | #[pinon|pon|on|high] [pin] : turns on the specified GPIO pin 15 | #[pinoff|poff|off|low] [pin] : turns off the specified GPIO pin 16 | #[write|w] [pin] [state] : writes specified state to the specified GPIO pin 17 | #[read|r] [pin]: reads the value of the specified GPIO pin 18 | #[available|online|busy|dnd|away|idle|out|xa] [arg1] : set gtalk state and status message to specified argument 19 | #[shell|bash] [arg1] : executes the specified shell command argument after ‘shell’ or ‘bash’ 20 | 21 | WORKDIR /raspi_gtalk_robot 22 | 23 | CMD ["python", "./raspiBot.py"] 24 | -------------------------------------------------------------------------------- /rpi-guvcview/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-x11-apps 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | guvcview \ 7 | --no-install-recommends \ 8 | && rm -rf /var/lib/apt/lists/* 9 | 10 | ENTRYPOINT ["guvcview"] 11 | -------------------------------------------------------------------------------- /rpi-hostapd/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | bridge-utils \ 7 | hostapd \ 8 | hostap-utils \ 9 | iw \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN echo "DAEMON_CONF=/etc/hostapd/hostapd.conf" >> /etc/init.d/hostapd 14 | 15 | ADD hostapd.conf /etc/hostapd/hostapd.conf 16 | 17 | #EXPOSE 67 18 | 19 | ENTRYPOINT ["bash"] 20 | -------------------------------------------------------------------------------- /rpi-hostapd/dnsmasq.conf: -------------------------------------------------------------------------------- 1 | no-resolv 2 | server=8.8.8.8 3 | interface=lo,wlan0 4 | no-dhcp-interface=lo 5 | dhcp-range=192.168.7.20,192.168.7.254,255.255.255.0,12h 6 | -------------------------------------------------------------------------------- /rpi-hostapd/hostapd.conf: -------------------------------------------------------------------------------- 1 | ssid=DockerAP 2 | interface=wlan0 3 | hw_mode=g 4 | channel=6 5 | wpa=2 6 | wpa_passphrase=dockerap123 7 | wpa_key_mgmt=WPA-PSK 8 | logger_syslog=-1 9 | logger_syslog_level=2 10 | logger_stdout=-1 11 | logger_stdout_level=2 12 | ctrl_interface=/var/run/hostapd 13 | -------------------------------------------------------------------------------- /rpi-iceweasel/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:wheezy 2 | 3 | MAINTAINER Michael J. Mitchell 4 | RUN apt-get update && apt-get install -y -q \ 5 | iceweasel \ 6 | --no-install-recommends && \ 7 | rm -rf /var/lib/apt/lists/* 8 | 9 | ENTRYPOINT ["iceweasel"] 10 | 11 | -------------------------------------------------------------------------------- /rpi-kalibrate/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | autoconf \ 7 | automake \ 8 | libfftw3-dev \ 9 | libtool \ 10 | pkg-config \ 11 | --no-install-recommends && \ 12 | rm -rf /var/lib/apt/lists/* 13 | 14 | RUN git clone https://github.com/asdil12/kalibrate-rtl.git && \ 15 | cd kalibrate-rtl && \ 16 | git checkout arm_memory && \ 17 | ./bootstrap && \ 18 | ./configure && \ 19 | make && \ 20 | make install 21 | 22 | #ENTRYPOINT ["kal", "-s", "GSM900"] 23 | ENTRYPOINT ["kal"] 24 | -------------------------------------------------------------------------------- /rpi-kitematic/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-node:0.12.0 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | ca-certificates \ 8 | git \ 9 | make \ 10 | libgtk2.0-0 \ 11 | libxtst6 \ 12 | libnotify-bin \ 13 | libgconf-2-4 \ 14 | libnss3 \ 15 | --no-install-recommends && \ 16 | rm -rf /var/lib/apt/lists/* 17 | 18 | WORKDIR / 19 | 20 | RUN git clone -b linux-support https://github.com/zedtux/kitematic 21 | 22 | WORKDIR /kitematic 23 | 24 | RUN npm install boom 25 | 26 | # electron 0.29 or higher is available for ARM 27 | RUN sed -i 's/"electron-version": "0.27.2",/"electron-version": "0.29.0",/' package.json 28 | 29 | RUN sed -i 's/"electron-prebuilt": "^0.27.3",/"electron-prebuilt": "^0.29.0",/' package.json 30 | 31 | # show some RPi images 32 | RUN sed -i 's,https://kitematic.com/recommended.json,http://blog.hypriot.com/recommended.json,' src/utils/RegHubUtil.js 33 | 34 | # enable web preview between containers 35 | RUN sed -i 's/var port = value\[0\].HostPort;/var port = dockerPort; ip = container.NetworkSettings.IPAddress;/' src/utils/ContainerUtil.js 36 | 37 | RUN npm install hoek 38 | RUN npm install is-property 39 | 40 | RUN make 41 | 42 | CMD ["npm", "start"] 43 | -------------------------------------------------------------------------------- /rpi-kivy-infoscreen/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-kivy 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | python-requests \ 7 | python-beautifulsoup \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | RUN git clone https://github.com/elParaguayo/RPi-InfoScreen-Kivy.git 12 | 13 | WORKDIR RPi-InfoScreen-Kivy/ 14 | 15 | CMD ["python", "main.py"] 16 | -------------------------------------------------------------------------------- /rpi-kivy/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | cython \ 8 | git-core \ 9 | gstreamer1.0-plugins-bad \ 10 | gstreamer1.0-plugins-base \ 11 | gstreamer1.0-plugins-good \ 12 | gstreamer1.0-plugins-ugly \ 13 | gstreamer1.0-alsa \ 14 | gstreamer1.0-omx \ 15 | libgl1-mesa-dev \ 16 | libgles2-mesa-dev \ 17 | libgstreamer1.0-dev \ 18 | libsdl2-dev \ 19 | libsdl2-image-dev \ 20 | libsdl2-mixer-dev \ 21 | libsdl2-ttf-dev \ 22 | pkg-config \ 23 | python-dev \ 24 | python-docutils \ 25 | python-pip \ 26 | python-setuptools \ 27 | --no-install-recommends && \ 28 | rm -rf /var/lib/apt/lists/* 29 | 30 | #RUN pip install git+https://github.com/kivy/kivy.git@master 31 | RUN git clone https://github.com/kivy/kivy && \ 32 | cd kivy && \ 33 | make && \ 34 | echo "export PYTHONPATH=$(pwd):\$PYTHONPATH" >> ~/.profile && \ 35 | . ~/.profile 36 | 37 | WORKDIR examples/demo/showcase 38 | 39 | CMD ["python", "main.py"] 40 | 41 | 42 | -------------------------------------------------------------------------------- /rpi-libreoffice/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-x11-apps 2 | #FROM resin/rpi-raspbian:jessie 3 | 4 | MAINTAINER Michael J. Mitchell 5 | 6 | RUN apt-get update && apt-get install -y -q \ 7 | libreoffice \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | CMD ["libreoffice"] 12 | -------------------------------------------------------------------------------- /rpi-lynx/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | lynx \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | ENTRYPOINT ["lynx"] 11 | -------------------------------------------------------------------------------- /rpi-midori/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | midori \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | CMD ["midori"] 11 | -------------------------------------------------------------------------------- /rpi-minecraft/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | wget \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN wget --no-check-certificate \ 11 | https://s3.amazonaws.com/assets.minecraft.net/pi/minecraft-pi-0.1.1.tar.gz && \ 12 | tar xvf minecraft-pi-0.1.1.tar.gz && \ 13 | rm minecraft-pi-0.1.1.tar.gz && \ 14 | cd mcpi 15 | 16 | CMD ["minecraft-pi"] 17 | -------------------------------------------------------------------------------- /rpi-motion/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | motion \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN sed -i -e 's/^daemon on/daemon off/' \ 11 | -e 's/^webcontrol_localhost on/webcontrol_localhost off/' \ 12 | -e 's/^stream_localhost on/stream_localhost off/' \ 13 | /etc/motion/motion.conf 14 | 15 | VOLUME /var/lib/motion 16 | 17 | EXPOSE 8080 8081 18 | 19 | CMD ["/usr/bin/motion"] 20 | -------------------------------------------------------------------------------- /rpi-motion/motion.conf: -------------------------------------------------------------------------------- 1 | # Rename this distribution example file to motion.conf 2 | # 3 | # This config file was generated by motion 3.2.12+git20140228 4 | 5 | 6 | ############################################################ 7 | # Daemon 8 | ############################################################ 9 | 10 | # Start in daemon (background) mode and release terminal (default: off) 11 | daemon off 12 | 13 | # File to store the process ID, also called pid file. (default: not defined) 14 | process_id_file /var/run/motion/motion.pid 15 | 16 | ############################################################ 17 | # Basic Setup Mode 18 | ############################################################ 19 | 20 | # Start in Setup-Mode, daemon disabled. (default: off) 21 | setup_mode off 22 | 23 | 24 | # Use a file to save logs messages, if not defined stderr and syslog is used. (default: not defined) 25 | ;logfile /tmp/motion.log 26 | 27 | # Level of log messages [1..9] (EMR, ALR, CRT, ERR, WRN, NTC, INF, DBG, ALL). (default: 6 / NTC) 28 | log_level 6 29 | 30 | # Filter to log messages by type (COR, STR, ENC, NET, DBL, EVT, TRK, VID, ALL). (default: ALL) 31 | log_type all 32 | 33 | ########################################################### 34 | # Capture device options 35 | ############################################################ 36 | 37 | # Videodevice to be used for capturing (default /dev/video0) 38 | # for FreeBSD default is /dev/bktr0 39 | videodevice /dev/video0 40 | 41 | # v4l2_palette allows to choose preferable palette to be use by motion 42 | # to capture from those supported by your videodevice. (default: 17) 43 | # E.g. if your videodevice supports both V4L2_PIX_FMT_SBGGR8 and 44 | # V4L2_PIX_FMT_MJPEG then motion will by default use V4L2_PIX_FMT_MJPEG. 45 | # Setting v4l2_palette to 2 forces motion to use V4L2_PIX_FMT_SBGGR8 46 | # instead. 47 | # 48 | # Values : 49 | # V4L2_PIX_FMT_SN9C10X : 0 'S910' 50 | # V4L2_PIX_FMT_SBGGR16 : 1 'BYR2' 51 | # V4L2_PIX_FMT_SBGGR8 : 2 'BA81' 52 | # V4L2_PIX_FMT_SPCA561 : 3 'S561' 53 | # V4L2_PIX_FMT_SGBRG8 : 4 'GBRG' 54 | # V4L2_PIX_FMT_SGRBG8 : 5 'GRBG' 55 | # V4L2_PIX_FMT_PAC207 : 6 'P207' 56 | # V4L2_PIX_FMT_PJPG : 7 'PJPG' 57 | # V4L2_PIX_FMT_MJPEG : 8 'MJPEG' 58 | # V4L2_PIX_FMT_JPEG : 9 'JPEG' 59 | # V4L2_PIX_FMT_RGB24 : 10 'RGB3' 60 | # V4L2_PIX_FMT_SPCA501 : 11 'S501' 61 | # V4L2_PIX_FMT_SPCA505 : 12 'S505' 62 | # V4L2_PIX_FMT_SPCA508 : 13 'S508' 63 | # V4L2_PIX_FMT_UYVY : 14 'UYVY' 64 | # V4L2_PIX_FMT_YUYV : 15 'YUYV' 65 | # V4L2_PIX_FMT_YUV422P : 16 '422P' 66 | # V4L2_PIX_FMT_YUV420 : 17 'YU12' 67 | # 68 | v4l2_palette 17 69 | 70 | # Tuner device to be used for capturing using tuner as source (default /dev/tuner0) 71 | # This is ONLY used for FreeBSD. Leave it commented out for Linux 72 | ; tunerdevice /dev/tuner0 73 | 74 | # The video input to be used (default: -1) 75 | # Should normally be set to 0 or 1 for video/TV cards, and -1 for USB cameras 76 | input -1 77 | 78 | # The video norm to use (only for video capture and TV tuner cards) 79 | # Values: 0 (PAL), 1 (NTSC), 2 (SECAM), 3 (PAL NC no colour). Default: 0 (PAL) 80 | norm 0 81 | 82 | # The frequency to set the tuner to (kHz) (only for TV tuner cards) (default: 0) 83 | frequency 0 84 | 85 | # Rotate image this number of degrees. The rotation affects all saved images as 86 | # well as movies. Valid values: 0 (default = no rotation), 90, 180 and 270. 87 | rotate 0 88 | 89 | # Image width (pixels). Valid range: Camera dependent, default: 352 90 | #width 320 91 | #width 640 92 | width 800 93 | 94 | # Image height (pixels). Valid range: Camera dependent, default: 288 95 | #height 240 96 | #height 480 97 | height 600 98 | 99 | # Maximum number of frames to be captured per second. 100 | # Valid range: 2-100. Default: 100 (almost no limit). 101 | #framerate 2 102 | framerate 100 103 | 104 | # Minimum time in seconds between capturing picture frames from the camera. 105 | # Default: 0 = disabled - the capture rate is given by the camera framerate. 106 | # This option is used when you want to capture images at a rate lower than 2 per second. 107 | minimum_frame_time 0 108 | 109 | # URL to use if you are using a network camera, size will be autodetected (incl http:// ftp:// mjpg:// rstp:// or file:///) 110 | # Must be a URL that returns single jpeg pictures or a raw mjpeg stream. Default: Not defined 111 | ; netcam_url value 112 | 113 | # Username and password for network camera (only if required). Default: not defined 114 | # Syntax is user:password 115 | ; netcam_userpass value 116 | 117 | # The setting for keep-alive of network socket, should improve performance on compatible net cameras. 118 | # off: The historical implementation using HTTP/1.0, closing the socket after each http request. 119 | # force: Use HTTP/1.0 requests with keep alive header to reuse the same connection. 120 | # on: Use HTTP/1.1 requests that support keep alive as default. 121 | # Default: off 122 | netcam_keepalive off 123 | 124 | # URL to use for a netcam proxy server, if required, e.g. "http://myproxy". 125 | # If a port number other than 80 is needed, use "http://myproxy:1234". 126 | # Default: not defined 127 | ; netcam_proxy value 128 | 129 | # Set less strict jpeg checks for network cameras with a poor/buggy firmware. 130 | # Default: off 131 | netcam_tolerant_check off 132 | 133 | # Let motion regulate the brightness of a video device (default: off). 134 | # The auto_brightness feature uses the brightness option as its target value. 135 | # If brightness is zero auto_brightness will adjust to average brightness value 128. 136 | # Only recommended for cameras without auto brightness 137 | auto_brightness off 138 | 139 | # Set the initial brightness of a video device. 140 | # If auto_brightness is enabled, this value defines the average brightness level 141 | # which Motion will try and adjust to. 142 | # Valid range 0-255, default 0 = disabled 143 | brightness 0 144 | 145 | # Set the contrast of a video device. 146 | # Valid range 0-255, default 0 = disabled 147 | contrast 0 148 | 149 | # Set the saturation of a video device. 150 | # Valid range 0-255, default 0 = disabled 151 | saturation 0 152 | 153 | # Set the hue of a video device (NTSC feature). 154 | # Valid range 0-255, default 0 = disabled 155 | hue 0 156 | 157 | 158 | ############################################################ 159 | # Round Robin (multiple inputs on same video device name) 160 | ############################################################ 161 | 162 | # Number of frames to capture in each roundrobin step (default: 1) 163 | roundrobin_frames 1 164 | 165 | # Number of frames to skip before each roundrobin step (default: 1) 166 | roundrobin_skip 1 167 | 168 | # Try to filter out noise generated by roundrobin (default: off) 169 | switchfilter off 170 | 171 | 172 | ############################################################ 173 | # Motion Detection Settings: 174 | ############################################################ 175 | 176 | # Threshold for number of changed pixels in an image that 177 | # triggers motion detection (default: 1500) 178 | threshold 1500 179 | 180 | # Automatically tune the threshold down if possible (default: off) 181 | threshold_tune off 182 | 183 | # Noise threshold for the motion detection (default: 32) 184 | noise_level 32 185 | 186 | # Automatically tune the noise threshold (default: on) 187 | noise_tune on 188 | 189 | # Despeckle motion image using (e)rode or (d)ilate or (l)abel (Default: not defined) 190 | # Recommended value is EedDl. Any combination (and number of) of E, e, d, and D is valid. 191 | # (l)abeling must only be used once and the 'l' must be the last letter. 192 | # Comment out to disable 193 | despeckle_filter EedDl 194 | 195 | # Detect motion in predefined areas (1 - 9). Areas are numbered like that: 1 2 3 196 | # A script (on_area_detected) is started immediately when motion is 4 5 6 197 | # detected in one of the given areas, but only once during an event. 7 8 9 198 | # One or more areas can be specified with this option. Take care: This option 199 | # does NOT restrict detection to these areas! (Default: not defined) 200 | ; area_detect value 201 | 202 | # PGM file to use as a sensitivity mask. 203 | # Full path name to. (Default: not defined) 204 | ; mask_file value 205 | 206 | # Dynamically create a mask file during operation (default: 0) 207 | # Adjust speed of mask changes from 0 (off) to 10 (fast) 208 | smart_mask_speed 0 209 | 210 | # Ignore sudden massive light intensity changes given as a percentage of the picture 211 | # area that changed intensity. Valid range: 0 - 100 , default: 0 = disabled 212 | lightswitch 0 213 | 214 | # Picture frames must contain motion at least the specified number of frames 215 | # in a row before they are detected as true motion. At the default of 1, all 216 | # motion is detected. Valid range: 1 to thousands, recommended 1-5 217 | minimum_motion_frames 1 218 | 219 | # Specifies the number of pre-captured (buffered) pictures from before motion 220 | # was detected that will be output at motion detection. 221 | # Recommended range: 0 to 5 (default: 0) 222 | # Do not use large values! Large values will cause Motion to skip video frames and 223 | # cause unsmooth movies. To smooth movies use larger values of post_capture instead. 224 | pre_capture 0 225 | 226 | # Number of frames to capture after motion is no longer detected (default: 0) 227 | post_capture 0 228 | 229 | # Event Gap is the seconds of no motion detection that triggers the end of an event. 230 | # An event is defined as a series of motion images taken within a short timeframe. 231 | # Recommended value is 60 seconds (Default). The value -1 is allowed and disables 232 | # events causing all Motion to be written to one single movie file and no pre_capture. 233 | # If set to 0, motion is running in gapless mode. Movies don't have gaps anymore. An 234 | # event ends right after no more motion is detected and post_capture is over. 235 | event_gap 60 236 | 237 | # Maximum length in seconds of a movie 238 | # When value is exceeded a new movie file is created. (Default: 0 = infinite) 239 | max_movie_time 0 240 | 241 | # Always save images even if there was no motion (default: off) 242 | emulate_motion off 243 | 244 | 245 | ############################################################ 246 | # Image File Output 247 | ############################################################ 248 | 249 | # Output 'normal' pictures when motion is detected (default: on) 250 | # Valid values: on, off, first, best, center 251 | # When set to 'first', only the first picture of an event is saved. 252 | # Picture with most motion of an event is saved when set to 'best'. 253 | # Picture with motion nearest center of picture is saved when set to 'center'. 254 | # Can be used as preview shot for the corresponding movie. 255 | output_pictures on 256 | 257 | # Output pictures with only the pixels moving object (ghost images) (default: off) 258 | output_debug_pictures off 259 | 260 | # The quality (in percent) to be used by the jpeg compression (default: 75) 261 | quality 75 262 | 263 | # Type of output images 264 | # Valid values: jpeg, ppm (default: jpeg) 265 | picture_type jpeg 266 | 267 | ############################################################ 268 | # FFMPEG related options 269 | # Film (movies) file output, and deinterlacing of the video input 270 | # The options movie_filename and timelapse_filename are also used 271 | # by the ffmpeg feature 272 | ############################################################ 273 | 274 | # Use ffmpeg to encode movies in realtime (default: off) 275 | ffmpeg_output_movies on 276 | 277 | # Use ffmpeg to make movies with only the pixels moving 278 | # object (ghost images) (default: off) 279 | ffmpeg_output_debug_movies off 280 | 281 | # Use ffmpeg to encode a timelapse movie 282 | # Default value 0 = off - else save frame every Nth second 283 | ffmpeg_timelapse 0 284 | 285 | # The file rollover mode of the timelapse video 286 | # Valid values: hourly, daily (default), weekly-sunday, weekly-monday, monthly, manual 287 | ffmpeg_timelapse_mode daily 288 | 289 | # Bitrate to be used by the ffmpeg encoder (default: 400000) 290 | # This option is ignored if ffmpeg_variable_bitrate is not 0 (disabled) 291 | ffmpeg_bps 500000 292 | 293 | # Enables and defines variable bitrate for the ffmpeg encoder. 294 | # ffmpeg_bps is ignored if variable bitrate is enabled. 295 | # Valid values: 0 (default) = fixed bitrate defined by ffmpeg_bps, 296 | # or the range 2 - 31 where 2 means best quality and 31 is worst. 297 | ffmpeg_variable_bitrate 0 298 | 299 | # Codec to used by ffmpeg for the video compression. 300 | # Timelapse mpegs are always made in mpeg1 format independent from this option. 301 | # Supported formats are: mpeg1 (ffmpeg-0.4.8 only), mpeg4 (default), and msmpeg4. 302 | # mpeg1 - gives you files with extension .mpg 303 | # mpeg4 or msmpeg4 - gives you files with extension .avi 304 | # msmpeg4 is recommended for use with Windows Media Player because 305 | # it requires no installation of codec on the Windows client. 306 | # swf - gives you a flash film with extension .swf 307 | # flv - gives you a flash video with extension .flv 308 | # ffv1 - FF video codec 1 for Lossless Encoding ( experimental ) 309 | # mov - QuickTime ( testing ) 310 | # ogg - Ogg/Theora ( testing ) 311 | ffmpeg_video_codec mpeg4 312 | 313 | # Use ffmpeg to deinterlace video. Necessary if you use an analog camera 314 | # and see horizontal combing on moving objects in video or pictures. 315 | # (default: off) 316 | ffmpeg_deinterlace off 317 | 318 | ############################################################ 319 | # SDL Window 320 | ############################################################ 321 | 322 | # Number of motion thread to show in SDL Window (default: 0 = disabled) 323 | sdl_threadnr 0 324 | 325 | ############################################################ 326 | # External pipe to video encoder 327 | # Replacement for FFMPEG builtin encoder for ffmpeg_output_movies only. 328 | # The options movie_filename and timelapse_filename are also used 329 | # by the ffmpeg feature 330 | ############################################################# 331 | 332 | # Bool to enable or disable extpipe (default: off) 333 | use_extpipe off 334 | 335 | # External program (full path and opts) to pipe raw video to 336 | # Generally, use '-' for STDIN... 337 | ;extpipe mencoder -demuxer rawvideo -rawvideo w=320:h=240:i420 -ovc x264 -x264encopts bframes=4:frameref=1:subq=1:scenecut=-1:nob_adapt:threads=1:keyint=1000:8x8dct:vbv_bufsize=4000:crf=24:partitions=i8x8,i4x4:vbv_maxrate=800:no-chroma-me -vf denoise3d=16:12:48:4,pp=lb -of avi -o %f.avi - -fps %fps 338 | 339 | 340 | 341 | ############################################################ 342 | # Snapshots (Traditional Periodic Webcam File Output) 343 | ############################################################ 344 | 345 | # Make automated snapshot every N seconds (default: 0 = disabled) 346 | snapshot_interval 0 347 | 348 | 349 | ############################################################ 350 | # Text Display 351 | # %Y = year, %m = month, %d = date, 352 | # %H = hour, %M = minute, %S = second, %T = HH:MM:SS, 353 | # %v = event, %q = frame number, %t = thread (camera) number, 354 | # %D = changed pixels, %N = noise level, \n = new line, 355 | # %i and %J = width and height of motion area, 356 | # %K and %L = X and Y coordinates of motion center 357 | # %C = value defined by text_event - do not use with text_event! 358 | # You can put quotation marks around the text to allow 359 | # leading spaces 360 | ############################################################ 361 | 362 | # Locate and draw a box around the moving object. 363 | # Valid values: on, off, preview (default: off) 364 | # Set to 'preview' will only draw a box in preview_shot pictures. 365 | locate_motion_mode off 366 | 367 | # Set the look and style of the locate box if enabled. 368 | # Valid values: box, redbox, cross, redcross (default: box) 369 | # Set to 'box' will draw the traditional box. 370 | # Set to 'redbox' will draw a red box. 371 | # Set to 'cross' will draw a little cross to mark center. 372 | # Set to 'redcross' will draw a little red cross to mark center. 373 | locate_motion_style box 374 | 375 | # Draws the timestamp using same options as C function strftime(3) 376 | # Default: %Y-%m-%d\n%T = date in ISO format and time in 24 hour clock 377 | # Text is placed in lower right corner 378 | text_right %Y-%m-%d\n%T-%q 379 | 380 | # Draw a user defined text on the images using same options as C function strftime(3) 381 | # Default: Not defined = no text 382 | # Text is placed in lower left corner 383 | ; text_left CAMERA %t 384 | 385 | # Draw the number of changed pixed on the images (default: off) 386 | # Will normally be set to off except when you setup and adjust the motion settings 387 | # Text is placed in upper right corner 388 | text_changes off 389 | 390 | # This option defines the value of the special event conversion specifier %C 391 | # You can use any conversion specifier in this option except %C. Date and time 392 | # values are from the timestamp of the first image in the current event. 393 | # Default: %Y%m%d%H%M%S 394 | # The idea is that %C can be used filenames and text_left/right for creating 395 | # a unique identifier for each event. 396 | text_event %Y%m%d%H%M%S 397 | 398 | # Draw characters at twice normal size on images. (default: off) 399 | text_double off 400 | 401 | 402 | # Text to include in a JPEG EXIF comment 403 | # May be any text, including conversion specifiers. 404 | # The EXIF timestamp is included independent of this text. 405 | ;exif_text %i%J/%K%L 406 | 407 | ############################################################ 408 | # Target Directories and filenames For Images And Films 409 | # For the options snapshot_, picture_, movie_ and timelapse_filename 410 | # you can use conversion specifiers 411 | # %Y = year, %m = month, %d = date, 412 | # %H = hour, %M = minute, %S = second, 413 | # %v = event, %q = frame number, %t = thread (camera) number, 414 | # %D = changed pixels, %N = noise level, 415 | # %i and %J = width and height of motion area, 416 | # %K and %L = X and Y coordinates of motion center 417 | # %C = value defined by text_event 418 | # Quotation marks round string are allowed. 419 | ############################################################ 420 | 421 | # Target base directory for pictures and films 422 | # Recommended to use absolute path. (Default: current working directory) 423 | target_dir /var/lib/motion 424 | 425 | # File path for snapshots (jpeg or ppm) relative to target_dir 426 | # Default: %v-%Y%m%d%H%M%S-snapshot 427 | # Default value is equivalent to legacy oldlayout option 428 | # For Motion 3.0 compatible mode choose: %Y/%m/%d/%H/%M/%S-snapshot 429 | # File extension .jpg or .ppm is automatically added so do not include this. 430 | # Note: A symbolic link called lastsnap.jpg created in the target_dir will always 431 | # point to the latest snapshot, unless snapshot_filename is exactly 'lastsnap' 432 | snapshot_filename %v-%Y%m%d%H%M%S-snapshot 433 | 434 | # File path for motion triggered images (jpeg or ppm) relative to target_dir 435 | # Default: %v-%Y%m%d%H%M%S-%q 436 | # Default value is equivalent to legacy oldlayout option 437 | # For Motion 3.0 compatible mode choose: %Y/%m/%d/%H/%M/%S-%q 438 | # File extension .jpg or .ppm is automatically added so do not include this 439 | # Set to 'preview' together with best-preview feature enables special naming 440 | # convention for preview shots. See motion guide for details 441 | picture_filename %v-%Y%m%d%H%M%S-%q 442 | 443 | # File path for motion triggered ffmpeg films (movies) relative to target_dir 444 | # Default: %v-%Y%m%d%H%M%S 445 | # Default value is equivalent to legacy oldlayout option 446 | # For Motion 3.0 compatible mode choose: %Y/%m/%d/%H%M%S 447 | # File extension .mpg or .avi is automatically added so do not include this 448 | # This option was previously called ffmpeg_filename 449 | movie_filename %v-%Y%m%d%H%M%S 450 | 451 | # File path for timelapse movies relative to target_dir 452 | # Default: %Y%m%d-timelapse 453 | # Default value is near equivalent to legacy oldlayout option 454 | # For Motion 3.0 compatible mode choose: %Y/%m/%d-timelapse 455 | # File extension .mpg is automatically added so do not include this 456 | timelapse_filename %Y%m%d-timelapse 457 | 458 | ############################################################ 459 | # Global Network Options 460 | ############################################################ 461 | # Enable or disable IPV6 for http control and stream (default: off ) 462 | ipv6_enabled off 463 | 464 | ############################################################ 465 | # Live Stream Server 466 | ############################################################ 467 | 468 | # The mini-http server listens to this port for requests (default: 0 = disabled) 469 | stream_port 8081 470 | 471 | # Quality of the jpeg (in percent) images produced (default: 50) 472 | stream_quality 50 473 | 474 | # Output frames at 1 fps when no motion is detected and increase to the 475 | # rate given by stream_maxrate when motion is detected (default: off) 476 | stream_motion off 477 | 478 | # Maximum framerate for stream streams (default: 1) 479 | stream_maxrate 10 480 | 481 | # Restrict stream connections to localhost only (default: on) 482 | stream_localhost off 483 | 484 | # Limits the number of images per connection (default: 0 = unlimited) 485 | # Number can be defined by multiplying actual stream rate by desired number of seconds 486 | # Actual stream rate is the smallest of the numbers framerate and stream_maxrate 487 | stream_limit 0 488 | 489 | # Set the authentication method (default: 0) 490 | # 0 = disabled 491 | # 1 = Basic authentication 492 | # 2 = MD5 digest (the safer authentication) 493 | stream_auth_method 0 494 | 495 | # Authentication for the stream. Syntax username:password 496 | # Default: not defined (Disabled) 497 | ; stream_authentication username:password 498 | 499 | 500 | ############################################################ 501 | # HTTP Based Control 502 | ############################################################ 503 | 504 | # TCP/IP port for the http server to listen on (default: 0 = disabled) 505 | webcontrol_port 8080 506 | 507 | # Restrict control connections to localhost only (default: on) 508 | webcontrol_localhost off 509 | 510 | # Output for http server, select off to choose raw text plain (default: on) 511 | webcontrol_html_output on 512 | 513 | # Authentication for the http based control. Syntax username:password 514 | # Default: not defined (Disabled) 515 | ; webcontrol_authentication username:password 516 | 517 | 518 | ############################################################ 519 | # Tracking (Pan/Tilt) 520 | ############################################################# 521 | 522 | # Type of tracker (0=none (default), 1=stepper, 2=iomojo, 3=pwc, 4=generic, 5=uvcvideo, 6=servo) 523 | # The generic type enables the definition of motion center and motion size to 524 | # be used with the conversion specifiers for options like on_motion_detected 525 | track_type 0 526 | 527 | # Enable auto tracking (default: off) 528 | track_auto off 529 | 530 | # Serial port of motor (default: none) 531 | ;track_port /dev/ttyS0 532 | 533 | # Motor number for x-axis (default: 0) 534 | ;track_motorx 0 535 | 536 | # Set motorx reverse (default: 0) 537 | ;track_motorx_reverse 0 538 | 539 | # Motor number for y-axis (default: 0) 540 | ;track_motory 1 541 | 542 | # Set motory reverse (default: 0) 543 | ;track_motory_reverse 0 544 | 545 | # Maximum value on x-axis (default: 0) 546 | ;track_maxx 200 547 | 548 | # Minimum value on x-axis (default: 0) 549 | ;track_minx 50 550 | 551 | # Maximum value on y-axis (default: 0) 552 | ;track_maxy 200 553 | 554 | # Minimum value on y-axis (default: 0) 555 | ;track_miny 50 556 | 557 | # Center value on x-axis (default: 0) 558 | ;track_homex 128 559 | 560 | # Center value on y-axis (default: 0) 561 | ;track_homey 128 562 | 563 | # ID of an iomojo camera if used (default: 0) 564 | track_iomojo_id 0 565 | 566 | # Angle in degrees the camera moves per step on the X-axis 567 | # with auto-track (default: 10) 568 | # Currently only used with pwc type cameras 569 | track_step_angle_x 10 570 | 571 | # Angle in degrees the camera moves per step on the Y-axis 572 | # with auto-track (default: 10) 573 | # Currently only used with pwc type cameras 574 | track_step_angle_y 10 575 | 576 | # Delay to wait for after tracking movement as number 577 | # of picture frames (default: 10) 578 | track_move_wait 10 579 | 580 | # Speed to set the motor to (stepper motor option) (default: 255) 581 | track_speed 255 582 | 583 | # Number of steps to make (stepper motor option) (default: 40) 584 | track_stepsize 40 585 | 586 | 587 | ############################################################ 588 | # External Commands, Warnings and Logging: 589 | # You can use conversion specifiers for the on_xxxx commands 590 | # %Y = year, %m = month, %d = date, 591 | # %H = hour, %M = minute, %S = second, 592 | # %v = event, %q = frame number, %t = thread (camera) number, 593 | # %D = changed pixels, %N = noise level, 594 | # %i and %J = width and height of motion area, 595 | # %K and %L = X and Y coordinates of motion center 596 | # %C = value defined by text_event 597 | # %f = filename with full path 598 | # %n = number indicating filetype 599 | # Both %f and %n are only defined for on_picture_save, 600 | # on_movie_start and on_movie_end 601 | # Quotation marks round string are allowed. 602 | ############################################################ 603 | 604 | # Do not sound beeps when detecting motion (default: on) 605 | # Note: Motion never beeps when running in daemon mode. 606 | quiet on 607 | 608 | # Command to be executed when an event starts. (default: none) 609 | # An event starts at first motion detected after a period of no motion defined by event_gap 610 | ; on_event_start value 611 | 612 | # Command to be executed when an event ends after a period of no motion 613 | # (default: none). The period of no motion is defined by option event_gap. 614 | ; on_event_end value 615 | 616 | # Command to be executed when a picture (.ppm|.jpg) is saved (default: none) 617 | # To give the filename as an argument to a command append it with %f 618 | ; on_picture_save value 619 | 620 | # Command to be executed when a motion frame is detected (default: none) 621 | ; on_motion_detected value 622 | 623 | # Command to be executed when motion in a predefined area is detected 624 | # Check option 'area_detect'. (default: none) 625 | ; on_area_detected value 626 | 627 | # Command to be executed when a movie file (.mpg|.avi) is created. (default: none) 628 | # To give the filename as an argument to a command append it with %f 629 | ; on_movie_start value 630 | 631 | # Command to be executed when a movie file (.mpg|.avi) is closed. (default: none) 632 | # To give the filename as an argument to a command append it with %f 633 | ; on_movie_end value 634 | 635 | # Command to be executed when a camera can't be opened or if it is lost 636 | # NOTE: There is situations when motion don't detect a lost camera! 637 | # It depends on the driver, some drivers dosn't detect a lost camera at all 638 | # Some hangs the motion thread. Some even hangs the PC! (default: none) 639 | ; on_camera_lost value 640 | 641 | ##################################################################### 642 | # Common Options for database features. 643 | # Options require database options to be active also. 644 | ##################################################################### 645 | 646 | # Log to the database when creating motion triggered picture file (default: on) 647 | ; sql_log_picture on 648 | 649 | # Log to the database when creating a snapshot image file (default: on) 650 | ; sql_log_snapshot on 651 | 652 | # Log to the database when creating motion triggered movie file (default: off) 653 | ; sql_log_movie off 654 | 655 | # Log to the database when creating timelapse movies file (default: off) 656 | ; sql_log_timelapse off 657 | 658 | # SQL query string that is sent to the database 659 | # Use same conversion specifiers has for text features 660 | # Additional special conversion specifiers are 661 | # %n = the number representing the file_type 662 | # %f = filename with full path 663 | # Default value: 664 | # Create tables : 665 | ## 666 | # Mysql 667 | # CREATE TABLE security (camera int, filename char(80) not null, frame int, file_type int, time_stamp timestamp(14), event_time_stamp timestamp(14)); 668 | # 669 | # Postgresql 670 | # CREATE TABLE security (camera int, filename char(80) not null, frame int, file_type int, time_stamp timestamp without time zone, event_time_stamp timestamp without time zone); 671 | # 672 | # insert into security(camera, filename, frame, file_type, time_stamp, text_event) values('%t', '%f', '%q', '%n', '%Y-%m-%d %T', '%C') 673 | ; sql_query insert into security(camera, filename, frame, file_type, time_stamp, event_time_stamp) values('%t', '%f', '%q', '%n', '%Y-%m-%d %T', '%C') 674 | 675 | 676 | ############################################################ 677 | # Database Options 678 | ############################################################ 679 | 680 | # database type : mysql, postgresql, sqlite3 (default : not defined) 681 | ; database_type value 682 | 683 | # database to log to (default: not defined) 684 | ; database_dbname value 685 | 686 | # The host on which the database is located (default: localhost) 687 | ; database_host value 688 | 689 | # User account name for database (default: not defined) 690 | ; database_user value 691 | 692 | # User password for database (default: not defined) 693 | ; database_password value 694 | 695 | # Port on which the database is located 696 | # mysql 3306 , postgresql 5432 (default: not defined) 697 | ; database_port value 698 | 699 | ############################################################ 700 | # Database Options For SQLite3 701 | ############################################################ 702 | 703 | # SQLite3 database (file path) (default: not defined) 704 | ; sqlite3_db value 705 | 706 | 707 | 708 | ############################################################ 709 | # Video Loopback Device (vloopback project) 710 | ############################################################ 711 | 712 | # Output images to a video4linux loopback device 713 | # The value '-' means next available (default: not defined) 714 | ; video_pipe value 715 | 716 | # Output motion images to a video4linux loopback device 717 | # The value '-' means next available (default: not defined) 718 | ; motion_video_pipe value 719 | 720 | 721 | ############################################################## 722 | # Thread config files - One for each camera. 723 | # Except if only one camera - You only need this config file. 724 | # If you have more than one camera you MUST define one thread 725 | # config file for each camera in addition to this config file. 726 | ############################################################## 727 | 728 | # Remember: If you have more than one camera you must have one 729 | # thread file for each camera. E.g. 2 cameras requires 3 files: 730 | # This motion.conf file AND thread1.conf and thread2.conf. 731 | # Only put the options that are unique to each camera in the 732 | # thread config files. 733 | ; thread /etc/motion/thread1.conf 734 | ; thread /etc/motion/thread2.conf 735 | ; thread /etc/motion/thread3.conf 736 | ; thread /etc/motion/thread4.conf 737 | 738 | -------------------------------------------------------------------------------- /rpi-mpg123/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | alsa-utils \ 7 | mpg123 \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | #RUN modprobe snd_bcm2835 12 | #RUN amixer cset numid=3 1 13 | #COPY audio.mp3 /audio.mp3 14 | 15 | ENTRYPOINT ["mpg123", "audio.mp3"] 16 | -------------------------------------------------------------------------------- /rpi-mpg123/audio.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mitchtech/rpi-dockerfiles/c90ca4fc58b3b0929f5a6f1eff52717abade210b/rpi-mpg123/audio.mp3 -------------------------------------------------------------------------------- /rpi-multimon-ng/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | libpulse-dev \ 7 | libx11-dev \ 8 | qt4-default \ 9 | qt4-qmake \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN git clone https://github.com/EliasOenal/multimon-ng.git && \ 14 | cd multimon-ng && \ 15 | #git reset --hard $commit_id && \ 16 | mkdir build && \ 17 | cd build && \ 18 | qmake ../multimon-ng.pro && \ 19 | make && \ 20 | make install && \ 21 | rm -rf /multimon-ng 22 | 23 | ENTRYPOINT ["multimon-ng"] 24 | -------------------------------------------------------------------------------- /rpi-neopixel/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | npm-debug.log 3 | -------------------------------------------------------------------------------- /rpi-neopixel/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-node:onbuild 2 | 3 | MAINTAINER Michael J. Mitchell -------------------------------------------------------------------------------- /rpi-neopixel/LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Hypriot 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | 23 | -------------------------------------------------------------------------------- /rpi-neopixel/README.md: -------------------------------------------------------------------------------- 1 | # rpi-node-neopixel-example 2 | 3 | This is a code example written in Node.js for a blog post on [blog.hypriot.com](http://blog.hypriot.com/post/drive-neopixels-in-docker/). 4 | 5 | ## Building the image 6 | 7 | On your Raspberry Pi you can clone this example with 8 | 9 | ```bash 10 | $ git clone https://github.com/hypriot/rpi-node-neopixel-example.git 11 | $ cd rpi-node-neopixel-example 12 | ``` 13 | 14 | Then build the Docker image with 15 | 16 | ```bash 17 | $ docker build -t node-neopixel . 18 | ``` 19 | 20 | ## Running the example 21 | 22 | Now run the NeoPixel example app on a Raspberry Pi B/B+ with this command 23 | 24 | ```bash 25 | $ docker run --cap-add SYS_RAWIO --device /dev/mem -d node-neopixel 26 | ``` 27 | 28 | On the Raspberry Pi 2 you have to use this command 29 | 30 | ```bash 31 | $ docker run --privileged -d node-neopixel 32 | ``` 33 | 34 | ## Acknowlegements 35 | 36 | Thanks to 37 | 38 | * @usefulthink to create the Node.js module - https://github.com/raspberry-node/node-rpi-ws281x-native 39 | * @richardghirst to port the WS281x library to Raspberry Pi 2 - https://github.com/richardghirst/rpi_ws281x 40 | 41 | ## License 42 | 43 | The MIT License (MIT) 44 | 45 | Copyright (c) 2015 Hypriot 46 | 47 | Permission is hereby granted, free of charge, to any person obtaining a copy 48 | of this software and associated documentation files (the "Software"), to deal 49 | in the Software without restriction, including without limitation the rights 50 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 51 | copies of the Software, and to permit persons to whom the Software is 52 | furnished to do so, subject to the following conditions: 53 | 54 | The above copyright notice and this permission notice shall be included in all 55 | copies or substantial portions of the Software. 56 | 57 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 58 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 59 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 60 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 61 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 62 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 63 | SOFTWARE. 64 | -------------------------------------------------------------------------------- /rpi-neopixel/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rpi-neopixel", 3 | "private": true, 4 | "version": "0.0.2", 5 | "description": "Node.js NeoPixel app in docker", 6 | "author": "mitchtech, hypriot, adafruit", 7 | "dependencies": { 8 | "rpi-ws281x-native": "0.7.2" 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /rpi-neopixel/server.js: -------------------------------------------------------------------------------- 1 | var ws281x = require('rpi-ws281x-native'); 2 | 3 | var NUM_LEDS = parseInt(process.argv[2], 10) || 8, 4 | pixelData = new Uint32Array(NUM_LEDS); 5 | 6 | var brightness = 128; 7 | 8 | ws281x.init(NUM_LEDS); 9 | 10 | 11 | var lightsOff = function () { 12 | for (var i = 0; i < NUM_LEDS; i++) { 13 | pixelData[i] = color(0, 0, 0); 14 | } 15 | ws281x.render(pixelData); 16 | ws281x.reset(); 17 | } 18 | 19 | var signals = { 20 | 'SIGINT': 2, 21 | 'SIGTERM': 15 22 | }; 23 | 24 | function shutdown(signal, value) { 25 | console.log('Stopped by ' + signal); 26 | lightsOff(); 27 | process.nextTick(function () { process.exit(0); }); 28 | } 29 | 30 | Object.keys(signals).forEach(function (signal) { 31 | process.on(signal, function () { 32 | shutdown(signal, signals[signal]); 33 | }); 34 | }); 35 | 36 | // ---- animation-loop 37 | var offset = 0; 38 | setInterval(function () { 39 | for (var i = 0; i < NUM_LEDS; i++) { 40 | pixelData[i] = wheel(((i * 256 / NUM_LEDS) + offset) % 256); 41 | } 42 | 43 | offset = (offset + 1) % 256; 44 | ws281x.render(pixelData); 45 | }, 1000 / 30); 46 | 47 | console.log('Rainbow started. Press +C to exit.'); 48 | 49 | // generate rainbow colors accross 0-255 positions. 50 | function wheel(pos) { 51 | pos = 255 - pos; 52 | if (pos < 85) { return color(255 - pos * 3, 0, pos * 3); } 53 | else if (pos < 170) { pos -= 85; return color(0, pos * 3, 255 - pos * 3); } 54 | else { pos -= 170; return color(pos * 3, 255 - pos * 3, 0); } 55 | } 56 | 57 | // generate integer from RGB value 58 | function color(r, g, b) { 59 | r = r * brightness / 255; 60 | g = g * brightness / 255; 61 | b = b * brightness / 255; 62 | return ((r & 0xff) << 16) + ((g & 0xff) << 8) + (b & 0xff); 63 | } 64 | -------------------------------------------------------------------------------- /rpi-netcat/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | RUN apt-get update && apt-get install -y -q \ 4 | netcat \ 5 | --no-install-recommends && \ 6 | rm -rf /var/lib/apt/lists/* 7 | 8 | ENTRYPOINT ["netcat"] 9 | -------------------------------------------------------------------------------- /rpi-nginx/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:wheezy 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-key adv --keyserver hkp://pgp.mit.edu:80 --recv-keys 7638D0442B90D010 6 | 7 | ENV DEBIAN_FRONTEND noninteractive 8 | 9 | RUN apt-get update && apt-get install -y -q \ 10 | ca-certificates \ 11 | nginx \ 12 | --no-install-recommends && \ 13 | rm -rf /var/lib/apt/lists/* 14 | 15 | RUN ln -sf /dev/stdout /var/log/nginx/access.log 16 | 17 | RUN ln -sf /dev/stderr /var/log/nginx/error.log 18 | 19 | VOLUME ["/var/cache/nginx"] 20 | 21 | EXPOSE 80 443 22 | 23 | CMD ["nginx", "-g", "daemon off;"] 24 | 25 | -------------------------------------------------------------------------------- /rpi-nmap/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | RUN apt-get update && apt-get install -y -q \ 4 | nmap \ 5 | --no-install-recommends && \ 6 | rm -rf /var/lib/apt/lists/* 7 | 8 | ENTRYPOINT ["nmap"] 9 | -------------------------------------------------------------------------------- /rpi-okular/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | okular \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | ENTRYPOINT ["okular"] 11 | 12 | -------------------------------------------------------------------------------- /rpi-opencv/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | git \ 7 | python \ 8 | python-dev \ 9 | python-pip \ 10 | python-virtualenv \ 11 | python-opencv \ 12 | python-all-dev \ 13 | libopencv-dev \ 14 | --no-install-recommends && \ 15 | rm -rf /var/lib/apt/lists/* 16 | 17 | VOLUME ["/data"] 18 | 19 | WORKDIR /data 20 | 21 | CMD ["bash"] 22 | -------------------------------------------------------------------------------- /rpi-openstf/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM openstf/armv7hf-stf 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | USER root 6 | 7 | RUN apt-get update && apt-get install -y -q \ 8 | android-tools* \ 9 | ca-certificates \ 10 | curl \ 11 | usbutils \ 12 | --no-install-recommends \ 13 | && rm -rf /var/lib/apt/lists/* 14 | 15 | # Set up insecure default key 16 | RUN mkdir -m 0750 /.android 17 | 18 | ADD insecure_shared_adbkey /.android/adbkey 19 | ADD insecure_shared_adbkey.pub /.android/adbkey.pub 20 | 21 | WORKDIR /data 22 | 23 | ENTRYPOINT [ "bash" ] 24 | 25 | CMD ["stf", "local"] 26 | -------------------------------------------------------------------------------- /rpi-pianobar/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:wheezy 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | openssl \ 7 | pianobar \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | RUN mkdir -m 0750 -p ~/.config/pianobar 12 | 13 | ADD config ~/.config/pianobar/config 14 | 15 | ADD tls_fingerprint.sh /bin/tls_fingerprint.sh 16 | 17 | RUN echo "tls_fingerprint = `tls_fingerprint.sh`" >> ~/.config/pianobar/config 18 | 19 | CMD ["pianobar"] 20 | -------------------------------------------------------------------------------- /rpi-pianobar/config: -------------------------------------------------------------------------------- 1 | # This is an example configuration file for pianobar. You may remove the # from 2 | # lines you need and copy/move this file to ~/.config/pianobar/config 3 | # See manpage for a description of the config keys 4 | # 5 | # User 6 | #user = your@user.name 7 | #password = password 8 | # or 9 | #password_command = gpg --decrypt ~/password 10 | 11 | # Proxy (for those who are not living in the USA) 12 | #control_proxy = http://127.0.0.1:9090/ 13 | 14 | # Keybindings 15 | #act_help = ? 16 | #act_songlove = + 17 | #act_songban = - 18 | #act_stationaddmusic = a 19 | #act_stationcreate = c 20 | #act_stationdelete = d 21 | #act_songexplain = e 22 | #act_stationaddbygenre = g 23 | #act_songinfo = i 24 | #act_addshared = j 25 | #act_songmove = m 26 | #act_songnext = n 27 | #act_songpause = S 28 | #act_songpausetoggle = p 29 | #act_songpausetoggle2 = 30 | #act_songplay = P 31 | #act_quit = q 32 | #act_stationrename = r 33 | #act_stationchange = s 34 | #act_stationcreatefromsong = v 35 | #act_songtired = t 36 | #act_upcoming = u 37 | #act_stationselectquickmix = x 38 | #act_voldown = ( 39 | #act_volup = ) 40 | #act_volreset = ^ 41 | 42 | # Misc 43 | #audio_quality = low 44 | #autostart_station = 123456 45 | #event_command = /home/user/.config/pianobar/eventcmd 46 | #fifo = /tmp/pianobar 47 | #sort = quickmix_10_name_az 48 | #love_icon = [+] 49 | #ban_icon = [-] 50 | #volume = 0 51 | #ca_bundle = /etc/ssl/certs/ca-certificates.crt 52 | 53 | # Format strings 54 | #format_nowplaying_song = 55 | n % 56 | #format_nowplaying_station = Stationmt_list_song = %i) %a - %t%r 57 | 58 | # high-quality audio (192k mp3, for Pandora One subscribers only!) 59 | #audio_quality = high 60 | #rpc_host = internal-tuner.pandora.com 61 | #partner_user = pandora one 62 | #partner_password = TVCKIBGS9AO9TSYLNNFUML0743LH82D 63 | #device = D01 64 | #encrypt_password = 2%3WCL*JU$MP]4 65 | #decrypt_password = U#IO$RZPAB%VX2 66 | -------------------------------------------------------------------------------- /rpi-pianobar/tls_fingerprint.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | ## 3 | ## A simple little shell script that will return the current 4 | ## fingerprint on the SSL certificate. It's crude but works :D 5 | ## 6 | ## Author: Bob Saska (r35krag0th) 7 | 8 | openssl s_client -connect tuner.pandora.com:443 < /dev/null 2> /dev/null | \ 9 | openssl x509 -noout -fingerprint | tr -d ':' | cut -d'=' -f2 10 | -------------------------------------------------------------------------------- /rpi-pifm-rds/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-pifm 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | libsndfile1-dev \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN git clone https://github.com/ChristopheJacquet/PiFmRds.git && \ 11 | cd PiFmRds/src && \ 12 | make 13 | 14 | WORKDIR /PiFmRds 15 | 16 | #CMD ["bash"] 17 | CMD ["./src/pi_fm_rds", "-freq", "103.0", "-audio", "./sound.wav", "-rt", "sound_file_text"] 18 | -------------------------------------------------------------------------------- /rpi-pifm/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | ca-certificates \ 8 | git \ 9 | gcc \ 10 | g++ \ 11 | make \ 12 | python \ 13 | --no-install-recommends && \ 14 | rm -rf /var/lib/apt/lists/* 15 | RUN git clone https://github.com/markondej/fm_transmitter.git && \ 16 | cd fm_transmitter && \ 17 | make 18 | 19 | WORKDIR /fm_transmitter 20 | 21 | #CMD ["bash"] 22 | CMD ["./fm_transmitter", "-f", "103.0", "./star_wars.wav"] 23 | -------------------------------------------------------------------------------- /rpi-pirate-radio/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-pifm 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | #RUN apt-get update && apt-get install -y -q \ 6 | # build-essential \ 7 | # ca-certificates \ 8 | # git \ 9 | # python \ 10 | # --no-install-recommends && \ 11 | # rm -rf /var/lib/apt/lists/* 12 | 13 | RUN git clone https://github.com/Make-Magazine/PirateRadio.git 14 | 15 | CMD ["python", "/PirateRadio/PirateRadio.py"] 16 | -------------------------------------------------------------------------------- /rpi-pirate-radio/pirateradio.conf: -------------------------------------------------------------------------------- 1 | [pirateradio] 2 | frequency = 103.0 3 | shuffle = True 4 | repeat_all = True 5 | stereo_playback = True 6 | music_dir = /pirateradio 7 | -------------------------------------------------------------------------------- /rpi-processing/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | wget \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN wget --no-check-certificate \ 11 | http://download.processing.org/processing-3.0.2-linux-armv6hf.tgz && \ 12 | tar xvfz processing-3.0.2-linux-armv6hf.tgz && \ 13 | rm processing-3.0.2-linux-armv6hf.tgz 14 | 15 | ENTRYPOINT ["/processing-3.0.2/processing"] 16 | -------------------------------------------------------------------------------- /rpi-pulseaudio/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | alsa-utils \ 7 | libasound2 \ 8 | libasound2-plugins \ 9 | pulseaudio \ 10 | pulseaudio-utils \ 11 | --no-install-recommends && \ 12 | rm -rf /var/lib/apt/lists/* 13 | 14 | ENV HOME /home/pulseaudio 15 | 16 | RUN useradd --create-home --home-dir $HOME pulseaudio && \ 17 | usermod -aG audio,pulse,pulse-access pulseaudio && \ 18 | chown -R pulseaudio:pulseaudio $HOME 19 | 20 | WORKDIR $HOME 21 | 22 | USER pulseaudio 23 | 24 | COPY default.pa /etc/pulse/default.pa 25 | COPY client.conf /etc/pulse/client.conf 26 | COPY daemon.conf /etc/pulse/daemon.conf 27 | 28 | ENTRYPOINT [ "pulseaudio" ] 29 | 30 | CMD [ "--log-level=4", "--log-target=stderr", "-v" ] 31 | -------------------------------------------------------------------------------- /rpi-pulseaudio/client.conf: -------------------------------------------------------------------------------- 1 | # This file is part of PulseAudio. 2 | # 3 | # PulseAudio is free software; you can redistribute it and/or modify 4 | # it under the terms of the GNU Lesser General Public License as published by 5 | # the Free Software Foundation; either version 2 of the License, or 6 | # (at your option) any later version. 7 | # 8 | # PulseAudio is distributed in the hope that it will be useful, but 9 | # WITHOUT ANY WARRANTY; without even the implied warranty of 10 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 11 | # General Public License for more details. 12 | # 13 | # You should have received a copy of the GNU Lesser General Public License 14 | # along with PulseAudio; if not, write to the Free Software 15 | # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 16 | # USA. 17 | 18 | ## Configuration file for PulseAudio clients. See pulse-client.conf(5) for 19 | ## more information. Default values are commented out. Use either ; or # for 20 | ## commenting. 21 | 22 | ; default-sink = 23 | ; default-source = 24 | ; default-server = 25 | ; default-dbus-server = 26 | 27 | autospawn = no 28 | daemon-binary = /bin/true 29 | ; extra-arguments = --log-target=syslog 30 | 31 | ; cookie-file = 32 | 33 | ; enable-shm = yes 34 | ; shm-size-bytes = 0 # setting this 0 will use the system-default, usually 64 MiB 35 | 36 | ; auto-connect-localhost = no 37 | ; auto-connect-display = no 38 | -------------------------------------------------------------------------------- /rpi-pulseaudio/daemon.conf: -------------------------------------------------------------------------------- 1 | # This file is part of PulseAudio. 2 | # 3 | # PulseAudio is free software; you can redistribute it and/or modify 4 | # it under the terms of the GNU Lesser General Public License as published by 5 | # the Free Software Foundation; either version 2 of the License, or 6 | # (at your option) any later version. 7 | # 8 | # PulseAudio is distributed in the hope that it will be useful, but 9 | # WITHOUT ANY WARRANTY; without even the implied warranty of 10 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 11 | # General Public License for more details. 12 | # 13 | # You should have received a copy of the GNU Lesser General Public License 14 | # along with PulseAudio; if not, see . 15 | 16 | ## Configuration file for the PulseAudio daemon. See pulse-daemon.conf(5) for 17 | ## more information. Default values are commented out. Use either ; or # for 18 | ## commenting. 19 | 20 | ; daemonize = no 21 | ; fail = yes 22 | ; allow-module-loading = yes 23 | ; allow-exit = yes 24 | ; use-pid-file = yes 25 | ; system-instance = no 26 | ; local-server-type = user 27 | ; enable-shm = yes 28 | ; shm-size-bytes = 0 # setting this 0 will use the system-default, usually 64 MiB 29 | ; lock-memory = no 30 | ; cpu-limit = no 31 | 32 | ; high-priority = yes 33 | ; nice-level = -11 34 | 35 | ; realtime-scheduling = yes 36 | ; realtime-priority = 5 37 | 38 | exit-idle-time = 180 39 | ; scache-idle-time = 20 40 | 41 | ; dl-search-path = (depends on architecture) 42 | 43 | ; load-default-script-file = yes 44 | ; default-script-file = /etc/pulse/default.pa 45 | 46 | ; log-target = auto 47 | ; log-level = notice 48 | ; log-meta = no 49 | ; log-time = no 50 | ; log-backtrace = 0 51 | 52 | ; resample-method = speex-float-1 53 | ; enable-remixing = yes 54 | ; enable-lfe-remixing = no 55 | 56 | flat-volumes = yes 57 | 58 | ; rlimit-fsize = -1 59 | ; rlimit-data = -1 60 | ; rlimit-stack = -1 61 | ; rlimit-core = -1 62 | ; rlimit-as = -1 63 | ; rlimit-rss = -1 64 | ; rlimit-nproc = -1 65 | ; rlimit-nofile = 256 66 | ; rlimit-memlock = -1 67 | ; rlimit-locks = -1 68 | ; rlimit-sigpending = -1 69 | ; rlimit-msgqueue = -1 70 | ; rlimit-nice = 31 71 | ; rlimit-rtprio = 9 72 | ; rlimit-rttime = 200000 73 | 74 | ; default-sample-format = s16le 75 | ; default-sample-rate = 44100 76 | ; alternate-sample-rate = 48000 77 | ; default-sample-channels = 2 78 | ; default-channel-map = front-left,front-right 79 | 80 | ; default-fragments = 4 81 | ; default-fragment-size-msec = 25 82 | 83 | ; enable-deferred-volume = yes 84 | ; deferred-volume-safety-margin-usec = 8000 85 | ; deferred-volume-extra-delay-usec = 0 86 | 87 | -------------------------------------------------------------------------------- /rpi-pulseaudio/default.pa: -------------------------------------------------------------------------------- 1 | # Replace the *entire* content of this file with these few lines and 2 | # read the comments 3 | 4 | .fail 5 | # Set tsched=0 here if you experience glitchy playback. This will 6 | # revert back to interrupt-based scheduling and should fix it. 7 | # 8 | # Replace the device= part if you want pulse to use a specific device 9 | # such as "dmix" and "dsnoop" so it doesn't lock an hw: device. 10 | 11 | # INPUT/RECORD 12 | load-module module-alsa-source device="default" tsched=1 13 | 14 | # OUTPUT/PLAYBACK 15 | load-module module-alsa-sink device="default" tsched=1 16 | 17 | # Accept clients -- very important 18 | load-module module-native-protocol-unix 19 | load-module module-native-protocol-tcp auth-ip-acl=127.0.0.1;192.168.0.0/24 auth-anonymous=1 20 | 21 | .nofail 22 | .ifexists module-x11-publish.so 23 | # Publish to X11 so the clients know how to connect to Pulse. Will 24 | # clear itself on unload. 25 | load-module module-x11-publish 26 | .endif 27 | -------------------------------------------------------------------------------- /rpi-python/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | python \ 7 | python-dev \ 8 | python-pip \ 9 | python-virtualenv \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | WORKDIR /data 14 | 15 | CMD ["bash"] 16 | -------------------------------------------------------------------------------- /rpi-radioplayer/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | mpc \ 7 | mpd \ 8 | unzip \ 9 | wget \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN wget https://learn.adafruit.com/system/assets/assets/000/019/200/original/Pi_Radio_player.zip && \ 14 | unzip Pi_Radio_player.zip && \ 15 | mv Pi\ Radio\ player pi-radio && \ 16 | rm Pi_Radio_player.zip && \ 17 | cd pi-radio 18 | 19 | CMD ["python", "radioplayer.py"] 20 | -------------------------------------------------------------------------------- /rpi-rethinkdb/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM armv7/armhf-ubuntu_core 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | curl \ 8 | g++ \ 9 | libboost-dev \ 10 | libprotobuf-dev \ 11 | m4 \ 12 | protobuf-compiler \ 13 | python \ 14 | wget \ 15 | --no-install-recommends && \ 16 | rm -rf /var/lib/apt/lists/* 17 | 18 | RUN wget http://download.rethinkdb.com/dist/rethinkdb-2.2.4.tgz && \ 19 | tar -zxvf rethinkdb-2.2.4.tgz && \ 20 | cd rethinkdb-2.2.4 && \ 21 | ./configure --with-system-malloc --allow-fetch && \ 22 | make ALLOW_WARNINGS=1 && \ 23 | make install ALLOW_WARNINGS=1 24 | 25 | VOLUME ["/data"] 26 | 27 | WORKDIR /data 28 | 29 | CMD ["rethinkdb", "--bind", "all"] 30 | 31 | EXPOSE 28015 29015 8080 32 | -------------------------------------------------------------------------------- /rpi-rpio/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | --no-install-recommends && \ 8 | rm -rf /var/lib/apt/lists/* 9 | 10 | RUN pip install rpio 11 | 12 | CMD ["bash"] 13 | 14 | -------------------------------------------------------------------------------- /rpi-rpitx/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | ca-certificates \ 8 | git \ 9 | imagemagick \ 10 | libsndfile1-dev \ 11 | --no-install-recommends && \ 12 | rm -rf /var/lib/apt/lists/* 13 | 14 | RUN mknod /dev/rpidatv-mb c 100 0 15 | 16 | RUN git clone https://github.com/F5OEO/rpitx.git && \ 17 | cd rpitx/src && \ 18 | make && \ 19 | make install 20 | 21 | CMD ["bash"] 22 | -------------------------------------------------------------------------------- /rpi-rtl-ais/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-sdr 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | pkg-config \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | RUN git clone https://github.com/dgiardini/rtl-ais.git && \ 12 | cd rtl-ais && \ 13 | make 14 | 15 | ENTRYPOINT ["/rtl-ais/rtl_ais"] 16 | -------------------------------------------------------------------------------- /rpi-sdr/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | cmake \ 8 | git \ 9 | libusb-1.0-0-dev \ 10 | python \ 11 | python-numpy \ 12 | python-pip \ 13 | --no-install-recommends && \ 14 | rm -rf /var/lib/apt/lists/* 15 | 16 | RUN echo 'blacklist dvb_usb_rtl28xxu' > /etc/modprobe.d/raspi-blacklist.conf && \ 17 | git clone git://git.osmocom.org/rtl-sdr.git && \ 18 | cd rtl-sdr && \ 19 | mkdir build && \ 20 | cd build && \ 21 | cmake ../ -DINSTALL_UDEV_RULES=ON -DDETACH_KERNEL_DRIVER=ON && \ 22 | make && \ 23 | make install && \ 24 | ldconfig 25 | 26 | RUN pip install pyrtlsdr 27 | -------------------------------------------------------------------------------- /rpi-synergy/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | build-essential \ 7 | cmake \ 8 | gcc \ 9 | libx11-dev \ 10 | libxtst-dev \ 11 | make \ 12 | unzip \ 13 | wget \ 14 | --no-install-recommends && \ 15 | rm -rf /var/lib/apt/lists/* 16 | 17 | RUN wget http://synergy.googlecode.com/files/synergy-1.4.15-Source.tar.gz && \ 18 | tar -xzf synergy-1.4.15-Source.tar.gz && \ 19 | cd synergy-1.4.15-Source && \ 20 | unzip ./tools/cryptopp562.zip -d ./tools/cryptopp562 21 | 22 | RUN sed -i -e 's/\/usr\/local\/include/\/usr\/include/' \ 23 | /synergy-1.4.15-Source/CMakeLists.txt && \ 24 | sed -i -e 's/march=native/march=armv7-a/' \ 25 | /synergy-1.4.15-Source/tools/CMakeLists.txt 26 | 27 | RUN cd /synergy-1.4.15-Source && \ 28 | cmake . && \ 29 | make && \ 30 | cp -a ./bin/. /usr/bin 31 | 32 | EXPOSE 24800 33 | 34 | CMD ["synergyc", "--name", "pi", "192.168.0.45"] 35 | 36 | -------------------------------------------------------------------------------- /rpi-tipboard/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM hypriot/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | redis-server \ 7 | supervisor \ 8 | --no-install-recommends && \ 9 | rm -rf /var/lib/apt/lists/* 10 | 11 | ADD supervisord.conf /etc/supervisor/supervisord.conf 12 | 13 | USER root 14 | 15 | RUN mkdir /root/logs 16 | 17 | RUN bash -c "cd /root && \ 18 | virtualenv tb-env && \ 19 | source /root/tb-env/bin/activate && \ 20 | pip install tipboard && \ 21 | tipboard create_project demo" 22 | 23 | EXPOSE 7272 24 | 25 | VOLUME /root/.tipboard 26 | 27 | CMD ["/usr/bin/supervisord", "-j", "/root/supervisord.pid"] 28 | -------------------------------------------------------------------------------- /rpi-tipboard/layout_config.yaml: -------------------------------------------------------------------------------- 1 | details: 2 | page_title: Dashboard 3 | layout: 4 | - row_1_of_2: 5 | - col_1_of_4: 6 | - tile_template: text 7 | tile_id: id_r1_c1 8 | title: Empty Tile 9 | classes: 10 | 11 | - col_2_of_4: 12 | - tile_template: pie_chart 13 | tile_id: id_r1_c2 14 | title: Empty Tile 15 | classes: 16 | 17 | - col_3_of_4: 18 | - tile_template: line_chart 19 | tile_id: id_r1_c3 20 | title: Empty Tile 21 | classes: 22 | 23 | - col_4_of_4: 24 | - tile_template: simple_percentage 25 | tile_id: id_r1_c4 26 | title: Empty Tile 27 | classes: 28 | 29 | - row_2_of_2: 30 | - col_1_of_4: 31 | - tile_template: listing 32 | tile_id: id_r2_c1 33 | title: Empty Tile 34 | classes: 35 | 36 | - col_2_of_4: 37 | - tile_template: bar_chart 38 | tile_id: id_r2_c2 39 | title: Empty Tile 40 | classes: 41 | 42 | - col_3_of_4: 43 | - tile_template: big_value 44 | tile_id: id_r2_c3 45 | title: Empty Tile 46 | classes: 47 | 48 | - col_4_of_4: 49 | - tile_template: fancy_listing 50 | tile_id: id_r2_c4 51 | title: Empty Tile 52 | classes: -------------------------------------------------------------------------------- /rpi-tipboard/settings-local.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | 4 | from __future__ import absolute_import 5 | from __future__ import division 6 | from __future__ import print_function 7 | from __future__ import unicode_literals 8 | 9 | PROJECT_NAME = '[PROJECT_NAME]' 10 | API_KEY = '[YOUR_PROTECTED_KEY]' 11 | -------------------------------------------------------------------------------- /rpi-tipboard/supervisord.conf: -------------------------------------------------------------------------------- 1 | [supervisord] 2 | nodaemon=true 3 | user=root 4 | logfile=/root/logs/supervisord.log 5 | childlogdir=/root/logs 6 | logfile_maxbytes=2MB 7 | logfile_backups=10 8 | loglevel=info 9 | directory=/root 10 | 11 | [supervisorctl] 12 | serverurl=unix:///var/run/supervisor.sock 13 | 14 | [unix_http_server] 15 | file=/var/run/supervisor.sock 16 | chmod=0700 17 | 18 | [rpcinterface:supervisor] 19 | supervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface 20 | 21 | [program:redis] 22 | command=/usr/bin/redis-server 23 | process_name=%(program_name)s 24 | user=root 25 | numprocs=1 26 | stdout_logfile=/root/logs/redis_stdout.log 27 | stdout_logfile_maxbytes=1MB 28 | stdout_logfile_backups=10 29 | stdout_capture_maxbytes=1MB 30 | stdout_logfile=/root/logs/redis_stderr.log 31 | stderr_logfile_maxbytes=1MB 32 | stderr_logfile_backups=10 33 | stderr_capture_maxbytes=1MB 34 | autostart=true 35 | 36 | [program:tipboard] 37 | command=/bin/bash -c "cd /root && source /root/tb-env/bin/activate && tipboard runserver 0.0.0.0 7272" 38 | user=root 39 | directory=/root 40 | process_name=%(program_name)s 41 | numprocs=1 42 | stdout_logfile=/root/logs/tipboard_stdout.log 43 | stdout_logfile_maxbytes=1MB 44 | stdout_logfile_backups=10 45 | stdout_capture_maxbytes=1MB 46 | stdout_logfile=/root/logs/tipboard_stderr.log 47 | stderr_logfile_maxbytes=1MB 48 | stderr_logfile_backups=10 49 | stderr_capture_maxbytes=1MB 50 | autorestart=true 51 | autostart=true 52 | -------------------------------------------------------------------------------- /rpi-uiautomator-boto/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/arm-adb 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | python \ 7 | python-dev \ 8 | python-pip \ 9 | python-virtualenv \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN pip install uiautomator influxdb boto3 14 | 15 | CMD ["adb", "devices"] 16 | -------------------------------------------------------------------------------- /rpi-uiautomator/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/arm-adb 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | python \ 7 | python-dev \ 8 | python-pip \ 9 | python-virtualenv \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN pip install uiautomator influxdb 14 | 15 | CMD ["adb", "devices"] 16 | -------------------------------------------------------------------------------- /rpi-video-looper/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | dbus \ 7 | fonts-freefont-ttf \ 8 | git \ 9 | libfreetype6 \ 10 | libraspberrypi-dev \ 11 | libsmbclient \ 12 | libssh-4 \ 13 | libssl1.0.0 \ 14 | wget \ 15 | --no-install-recommends && \ 16 | rm -rf /var/lib/apt/lists/* 17 | 18 | RUN wget http://omxplayer.sconde.net/builds/omxplayer_0.3.7~git20160206~cb91001_armhf.deb && \ 19 | dpkg -i omxplayer_0.3.7~git20160206~cb91001_armhf.deb && \ 20 | apt-get install -f 21 | 22 | RUN git clone git://github.com/adafruit/pi_video_looper.git && \ 23 | cd pi_video_looper && \ 24 | ./install.sh 25 | 26 | CMD ["bash"] 27 | -------------------------------------------------------------------------------- /rpi-vnc/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | tightvncserver \ 7 | --no-install-recommends \ 8 | && rm -rf /var/lib/apt/lists/* 9 | 10 | RUN mkdir -p /.vnc 11 | 12 | RUN echo password | vncpasswd -f > /.vnc/passwd 13 | 14 | RUN chmod 600 /.vnc/passwd 15 | 16 | EXPOSE 5901 17 | 18 | CMD vncserver :1 -name vnc -geometry 800x640 && tail -f /.vnc/*:1.log 19 | 20 | #CMD ["vncserver", ":1"] 21 | -------------------------------------------------------------------------------- /rpi-webide/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | #FROM hypriot/rpi-node 3 | 4 | MAINTAINER Michael J. Mitchell 5 | 6 | RUN apt-get update && apt-get install -y -q \ 7 | build-essential \ 8 | git \ 9 | nodejs \ 10 | nodejs-legacy \ 11 | npm \ 12 | redis-server \ 13 | --no-install-recommends && \ 14 | rm -rf /var/lib/apt/lists/* 15 | 16 | RUN git clone git://github.com/adafruit/Adafruit-WebIDE.git && \ 17 | cd Adafruit-WebIDE && \ 18 | mkdir tmp && \ 19 | npm config set tmp tmp && \ 20 | npm install 21 | #editor config/config.js (change port 80 to your port of choice) 22 | 23 | ENTRYPOINT ["nodejs", "server.js"] 24 | 25 | -------------------------------------------------------------------------------- /rpi-wiringpi/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM mitchtech/rpi-python 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | 6 | RUN apt-get update && apt-get install -y -q \ 7 | build-essential \ 8 | gcc \ 9 | git-core \ 10 | --no-install-recommends && \ 11 | rm -rf /var/lib/apt/lists/* 12 | 13 | RUN git clone git://git.drogon.net/wiringPi && \ 14 | cd wiringPi && \ 15 | ./build && \ 16 | pip install pyserial wiringpi2 17 | 18 | WORKDIR /data 19 | 20 | VOLUME /data 21 | 22 | CMD ["bash"] 23 | -------------------------------------------------------------------------------- /rpi-x11-apps/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM resin/rpi-raspbian:jessie 2 | 3 | MAINTAINER Michael J. Mitchell 4 | 5 | RUN apt-get update && apt-get install -y -q \ 6 | x11-apps \ 7 | --no-install-recommends \ 8 | && rm -rf /var/lib/apt/lists/* 9 | 10 | CMD ["bash"] 11 | --------------------------------------------------------------------------------