#A sample project to demonstrate the usage of floto
##Configuration of am Host First set the following parameters
setDomain("sample.site");
var hostname = "sample-host";
var hostIp = "X.X.X.X";
var nameserver = hostIp;
var hypervisorType = "YYY";
var ovaUrl = "http://xyz.com/my.ova";
var networks = [];
var restPort = 2375;The Hypervisortype can be "virtualbox", "vmware", or "esx". The ovaUrl ist the File of the Virtualhost.
To define the Host you have to follow ths structure:
host(hostname,
{
name: hostname,
ip: hostIp,
vmConfiguration: {
ovaUrl: ovaUrl,
numberOfCores: 1,
memoryInMB: 2048,
hypervisor: {
type: hypervisorType
},
networks: networks
},
postDeploy: function postDeploy(host) {
...
},
reconfigure: function reconfigure(host, config) {
...
}
}
);Here are the parameters of the host and the build methods defined. ###Define hostname in machine
run("echo " + host.name + " > /etc/hostname ");
run("sudo start hostname ");
run("pkill -f \"/sbin/getty.*tty[1-6]\" || true");
run("sed -i 's/^127.0.1.1.*/127.0.1.1 " + host.name + "." + site.domainName + " " + host.name + "/' /etc/hosts");
...
run("echo -e 'search " + site.domainName + "\n' > /etc/resolvconf/resolv.conf.d/base");
run("resolvconf -u");
determineIp("hostname -I | cut -d ' ' -f2");###Configure Interfaces You need three interfaces for communication in your VM.
- eth0: for the internal network.
- eht1: for the communication with the host.
- eth2: for the communication with the internet.
// Configure network
var interfaces = [
// internal network
{
name: "eth0",
type: "static",
address: host.ip,
netmask: "255.255.255.0",
nameserver: nameserver
}
];
if(hypervisorType != "virtualbox"){
interfaces.push({
name: "eth1",
type: "dhcp"
});
}else{
interfaces.push({
// network for communication with rest of the world
name: "eth2",
type: "dhcp"
});
if(system != "windows"){
// network for communication with vbox-host
// Interface set in Java
interfaces.push({
// network for communication with vbox-host
name: "eth1",
type: "dhcp"
});
}
}
addTemplate(__DIR__ + "templates/network-interfaces.txt", "/etc/network/interfaces", {
interfaces: interfaces
});
run("ifdown eth0; ifup eth0");
if(hypervisorType != "virtualbox" && system != "windows"){
run("ifdown eth1; ifup eth1");
}else{
//Set automatically IP in JAVA
//Only with Windows and Virtualbox
setHostOnlyIpVBoxWin(hostname);
}
if(hypervisorType == "virtualbox") {
run("ifdown eth2; ifup eth2");
}You can use for the interfaces eth1 and eth2 dhcp except of when you are using floto under windows with virtualbox. Then you have to configure the interfaces like in the example. The configuration checks if the OS is Windwos and the Hypervisortype is virtualbox. If so then the configuration of the interface makes a Method in the Back-End.
###Create folders for volumes One folder for each Image
run("mkdir /usr/local/nginx");
run("mkdir /usr/local/nexus");
run("mkdir /usr/local/jenkins");
run("mkdir /usr/local/gitolite");###Restart Docker
run("sudo service docker restart");###Set Avahi
run('echo "AVAHI_DAEMON_DETECT_LOCAL=0\nAVAHI_DAEMON_START=1\n" > /etc/default/avahi-daemon');
run('echo "\n[server]\nallow-interfaces=eth1\n" >> /etc/avahi/avahi-daemon.conf');
run('/etc/init.d/avahi-daemon restart');###Bash Promt
var domainPrompt = site.projectName || (site.domainName.replace("\.site$", "").toUpperCase());
run("echo 'export PS1=\"\\u@\\h [" + domainPrompt + "] :\\w\\n\\$ \"' >> /home/user/.bashrc");###Docker logrotate
var dockerLogrotate = "/etc/logrotate.d/docker";
addTemplate(__DIR__ + "templates/logrotate-docker", dockerLogrotate);
run("chown root:root " + dockerLogrotate);###Format Disk if needed
if (host.vmConfiguration.disks != null) {
disks = _.cloneDeep(host.vmConfiguration.disks);
disks.forEach(function (disk, index) {
disk.deviceName = "/dev/sd" + String.fromCharCode(97 + 1 + index);
});
var partitionPath = "/tmp/partition.sh";
addTemplate(__DIR__ + "templates/partition.sh", partitionPath, {disks: disks});
run("chmod a+x " + partitionPath);
run(partitionPath);
}###Set Login-screen
var updateIssuePath = "/etc/network/if-up.d/update-issue";
addTemplate(__DIR__ + "templates/update-issue.sh", updateIssuePath, {
domainName: site.domainName,
useDhcp: true
});
run("chmod a+x " + updateIssuePath);
run("MODE=start " + updateIssuePath);###Reconfigure In reconfigure you have to add the docker-script to your host and run it.
addTemplate(__DIR__ + "templates/docker-reconfigure.sh", "/tmp/docker-reconfigure.sh", {httpProxy: config.httpProxy});
run("bash /tmp/docker-reconfigure.sh > /tmp/docker-reconfigure.log");###For configuration there are following methods
| Method | Meaning |
|---|---|
| run("command") | Command in Commandline |
| addTemplate("name","destination","config") | Add Template to host |
| determineIp("") | define a Ip |
##Configuration of an Image An image has the following structure.
image("imagename", {
build: function() {
...
},
prepare: function(config, container) {
...
},
configure: function(config) {
...
}
});to every image you can add an container
container("containername", {
image: "imagename",
host: hostname
});The imagename should give a hint about whot kind of service the image provides. In the build-function you can add all cammands which have to be in the dockerfile. Out of the commands in the build-function floto builds a dockerfile for the image. In the prepare-function you can add for example the link to the web-interface of this service.
config.webUrl = "http://" + hostname + ".local" + "/imagename";##Dockerfile Example
from("dockerfile/ubuntu");
// Mount Data on Host-Volume
volume("/usr/local/nexus","/opt/nexus");
//Add User
//run("sudo useradd -d /home/nexus -m --password nexus nexus");
run("apt-get update");
run("apt-get install -y openjdk-7-jre-headless");
run("apt-get install -y wget");
run("mkdir -p /root/opt/sonatype-nexus");
run("chmod 777 /root/opt/sonatype-nexus");
run("mkdir -p /root/opt/sonatype-work");
run("chmod 777 /root/opt/sonatype-work");
run("mkdir -p /root/opt/sonatype-work/nexus");
run("chmod 777 /root/opt/sonatype-work/nexus");
run("wget http://www.sonatype.org/downloads/nexus-latest-bundle.tar.gz ");
run("tar xvzf nexus-latest-bundle.tar.gz");
run("mv nexus-2.11.1-01/ /root/opt/sonatype-nexus");
run("useradd --user-group --system --home-dir /root/opt/sonatype-nexus nexus");
run("chown -R nexus:nexus /root/opt/sonatype-work /root/opt/sonatype-nexus /root/opt/sonatype-work/nexus");
runAsUser("nexus");
env("RUN_AS_USER", "root");
expose("8081");
cmd("/root/opt/sonatype-nexus/nexus-2.11.1-01/bin/nexus start");Here we see an configuration of an image for nexus. The methods mean this:
| floto | Dockerfile |
|---|---|
| from("baseimage") | FROM |
| run("command") | RUN |
| runAsUser("user") | USER |
| env("key","value") | ENV |
| expose("port") | EXPOSE |
| workdir("dir") | WORKDIR |
| cmd("command") | CMD |
| volume("path", "name") | VOLUME |
| mount("hostpath", "containerpath") | MOUNT |
| addTemplate("name","destination","config") | ADD |
##User-Overrides to make your configuration portable you can add a override method where some parameters are changed.
var userOverridesFile = __DIR__ + "user-overrides.js";
if(new java.io.File(userOverridesFile).exists()) {
include(userOverridesFile);
}in this file you can change this parameters
hypervisorType = "virtualbox"
ovaUrl = "file:X:/your/file/path/to/floto/image.ova"
networks = ["VM Network", "DHCP"]##Example for an NGINX image The configuration of NGINX in floto looks like this:
image("nginx", {
build: function() {
from("dockerfile/ubuntu");
run("sudo apt-get update");
run("sudo apt-get install -y nginx");
run("sudo apt-get install -y curl");
//Add User
run("sudo useradd -d /home/nginx -m --password nginx nginx");
// Mount Data on Host-Volume
volume("/usr/local/nginx","/opt/nginx");
// Change Config
// Put Config-File to Container
run('cd /etc/nginx/sites-available/');
run('touch reverse-proxy.conf');
addTemplate(__DIR__ + "templates/nginxreverse.conf", "/etc/nginx/sites-available/nginxreverse.conf", {hostname : hostname});
run('echo "\\ndaemon off;" >> /etc/nginx/nginx.conf');
expose('80');
cmd("nginx");
},
prepare: function(config, container) {
config.webUrl = "http://" + hostname + ".local" + "/nginx";
},
configure: function(config) {
}
});
container("nginx", {
image: "nginx",
host: hostname
});##Including configuration into floto First you have to open Eclipse and make a new run configuration. Set the main class to the "Floto-Server" class. Put following in the Argumentes:
--dev
--root /path/to/your/floto-example/sample-vbox.js
when you run this configuration you can open floto in your webbrowser with http://localhost:40004/