Fork me on GitHub
$ pip3 install plash > /dev/null
$ # for unprivileged usage, ensure you have unionfs-fuse and
$ # uidmap/shadow-utils installed
$ plash init
$ echo 'plash reference' | plash run --from ubuntu --apt figlet -- figlet
       _           _                 __
 _ __ | | __ _ ___| |__    _ __ ___ / _| ___ _ __ ___ _ __   ___ ___
| '_ \| |/ _` / __| '_ \  | '__/ _ \ |_ / _ \ '__/ _ \ '_ \ / __/ _ \
| |_) | | (_| \__ \ | | | | | |  __/  _|  __/ | |  __/ | | | (_|  __/
| .__/|_|\__,_|___/_| |_| |_|  \___|_|  \___|_|  \___|_| |_|\___\___|
|_|

$
$ plash --help
plash --help  List all available subcommands
plash --help-macros  Lists all available macros
plash --version  Prints the version number
plash -h  List all available subcommands
plash add-layer  Stack a layer on top of a container
plash build  Builds a container
plash clean  Cleanup internal states
plash create  Creates a new container from a command
plash data  Prints the location of the build data
plash eval  Generates a build script
plash export-tar  Export container as tar archive
plash help  List all available subcommands
plash help-macros  Lists all available macros
plash import-docker  Import image from local docker instance into
plash import-lxc  Import image from linuxcontainers
plash import-tar  Create a container from a tar file
plash import-url  Import a container from an url
plash init  Initialize build data
plash map  Map a container to a key
plash mount  Mount a container-filsystem
plash nodepath  Prints the path to a given container
plash parent  Prints the containers parent container
plash purge  Deletes all build data unatomically
plash rm  Deletes the given container atomically
plash run  Run a container
plash runopts  Run a container specifying lower level options
plash shallow-copy  Copy and hard link the filesystem to OUT
plash shrink  Delete half of the older containers
plash sudo  Setup a Linux user namespace
plash test  Run unit tests
plash version  Prints the version number
plash with-mount  Execute parameters inside a mounted container
plash -*  Fallback to `plash run`
$
$
$
$
$
$ echo 'tutorial' | plash -U --apt figlet -- figlet
  _         _             _       _
 | |_ _   _| |_ ___  _ __(_) __ _| |
 | __| | | | __/ _ \| '__| |/ _` | |
 | |_| |_| | || (_) | |  | | (_| | |
  \__|\__,_|\__\___/|_|  |_|\__,_|_|

$ ### plash works completly in user mode
$ whoami
myuser
$
$ ### fetch an alpine container from http://images.linuxcontainers.org/
$ plash build --from alpine
plash: fetching 100%
plash: extracting...
plash: ignoring dev file: ./dev/null (Operation not permitted)
2
$
$ ### run something on the container
$ plash run 2 printf 'hello from container\n'
hello from container
$
$ ### host filesystem is mapped to the container
$ mkdir ~/mydir
$ cd ~/mydir
$ plash run 2 pwd
/home/myuser/mydir
$
$ ### build a layer on top a container
$ plash build --from 2 --run 'touch /myfile'
+ touch /myfile
--:
3
$
$ ### build already cached
$ plash build --from 2 --run 'touch /myfile'
3
$
$ ### build and run in one command
$ plash run --from alpine --run 'touch /myfile' -- ls /myfile
/myfile
$
$ ### less verbose invocation
$ plash -Ax 'touch /myfile' -- ls /myfile
/myfile
$
$ ### explicit layering (`touch /myfile` is already cached)
$ plash -Ax 'touch /myfile' -lx 'touch /otherfile' -- ls /otherfile
+ touch /otherfile
--:
/otherfile
$
$ ### execute a command on the container's rootfs from the host
$ plash with-mount -A -- ls
bin  dev  etc  home  lib  media  mnt  proc  root  run  sbin  srv  sys  tmp  usr  var
$
$ ### use a docker image from a local docker instance
$ plash --from-docker busybox
Using default tag: latest
latest: Pulling from library/busybox
Digest: sha256:cb63aa0641a885f54de20f61d152187419e8f6b159ed11a251a09d115fdff9bd
Status: Image is up to date for busybox:latest
/home/myuser # exit
$
$ ### export a plash container to docker
$ ihucos@macbook:~/plash$ plash export-tar 2 | docker import -
sha256:2c3550e60fef9db8b154a45c04253506e7a9d585af8b738fbe39350d58cbd6ad
$
$ ### use an image published via github
$ plash --from-github ihucos/python
+ apk update
fetch http://dl-cdn.alpinelinux.org/alpine/v3.8/main/x86_64/APKINDEX.tar.gz
fetch http://dl-cdn.alpinelinux.org/alpine/v3.8/community/x86_64/APKINDEX.tar.gz
v3.8.1-5-g769378a189 [http://dl-cdn.alpinelinux.org/alpine/v3.8/main]
v3.8.1-1-g91d49cb572 [http://dl-cdn.alpinelinux.org/alpine/v3.8/community]
OK: 9540 distinct packages available
+ apk add curl git openssh-client py3-pip python3 python py-pip
(1/24) Installing ca-certificates (20171114-r3)
(2/24) Installing nghttp2-libs (1.32.0-r0)
(3/24) Installing libssh2 (1.8.0-r3)
...
...
...
(23/24) Installing py3-setuptools (39.1.0-r0)
(24/24) Installing py2-pip (10.0.1-r0)
Executing busybox-1.28.4-r1.trigger
Executing ca-certificates-20171114-r3.trigger
OK: 140 MiB in 42 packages
--:
myhost:/home/myuser/# python3 --version
Python 3.6.6
myhost:/home/myuser/# exit
$
$ ### remove the image (actually the last layer of it)
$ plash rm --from-github ihucos/python
$
$ ### create an executable build file
$ ed
a
#!/usr/bin/env plash-exec
--from-github ihucos/python
--pip3 yapf
--entrypoint /usr/bin/yapf
.
w /tmp/yapf
93
q
$ chmod +x /tmp/yapf
$ /tmp/yapf
+ pip3 install yapf
Collecting yapf
  Downloading https://files.pythonhosted.org/packages/32/12/9f6...08a/yapf-0.24.0-py2.py3-none-any.whl (168kB)
    100% |████████████████████████████████| 174kB 1.6MB/s 
Installing collected packages: yapf
Successfully installed yapf-0.24.0
--:
yapf 0.24.0
$ /tmp/yapf # second call is already cached
yapf 0.24.0
$
$ ### check the output of an sample of the build configuration management language
$ plash eval --from ubuntu --apt python3-pip --layer --pip3 yapf -lx 'touch /foo'
### plash hint: image=9
apt-get update
apt-get install -y python3-pip
### plash hint: layer
pip3 install yapf
### plash hint: layer
touch /foo
$ 
$
$
$ echo 'macros' | plash -U figlet -- figlet
                                    
 _ __ ___   __ _  ___ _ __ ___  ___ 
| '_ ` _ \ / _` |/ __| '__/ _ \/ __|
| | | | | | (_| | (__| | | (_) \__ \
|_| |_| |_|\__,_|\___|_|  \___/|___/
                                    
$ ### list vailable build commands (macros)
$ plash --help-macros
[plash.eval]
hint             = write a hint for consumer programs
import           = import macros from any python module
reset-imports    = unimport all imported macros but builtins

[plash.macros.common]
entrypoint       = hint default command for this build
entrypoint-script = write lines to /entrypoint and hint it as default command
eval-file        = evaluate file content as expressions
eval-stdin       = evaluate expressions read from stdin
eval-string      = evaluate expressions passed as string
hash-path        = recursively hash files and add as cache key
import-env       = import environment variables from host
invalidate-layer = invalidate the cache of the current layer
layer            = hint the start of a new layer
run              = directly emit shell script
run-stdin        = run commands read from stdin
write-file       = write lines to a file
write-script     = write an executable (755) file to the filesystem

[plash.macros.froms]
from             = guess from where to take the image
from-docker      = use image from local docker
from-github      = build and use a file (default 'plashfile') from github repo
from-id          = specify the image from an image id
from-lxc         = use images from images.linuxcontainers.org
from-map         = use resolved map as image
from-url         = import image from an url

[plash.macros.packagemanagers]
add-apt-repository = install packages with add-apt-repository
apk              = install packages with apk
apt              = install packages with apt
defpm            = define a new package manager
dnf              = install packages with dnf
emerge           = install packages with emerge
npm              = install packages with npm
pacman           = install packages with pacman
pip              = install packages with pip
pip3             = install packages with pip3
yum              = install packages with yum

[plash.macros.shortcuts]
A                = alias for: --from alpine --apk [ARG1 [ARG2 [...]]]
C                = alias for: --from centos --yum [ARG1 [ARG2 [...]]]
D                = alias for: --from debian --apt [ARG1 [ARG2 [...]]]
F                = alias for: --from fedora --dnf [ARG1 [ARG2 [...]]]
G                = alias for: --from gentoo --emerge [ARG1 [ARG2 [...]]]
R                = alias for: --from archlinux --pacman [ARG1 [ARG2 [...]]]
U                = alias for: --from ubuntu --apt [ARG1 [ARG2 [...]]]
f                = alias for: --from [ARG1 [ARG2 [...]]]
l                = alias for: --layer [ARG1 [ARG2 [...]]]
x                = alias for: --run [ARG1 [ARG2 [...]]]
$
$ exit # bye bye, check it out at github: https://github.com/ihucos/plash