 Hwyl, rydyn ni'n David White. Rydyn ni'n gweithio sig ysgai, yn y Games Skygo, ac mae yn nodi am dweud eu bod i ymell yn jedi arnyn nhw yn dweud. Gweithio yn i ddweud ar ni, ac mae Skygo yn dweud ag o anghlo. Rydych chi'n clyw'n dim yn dweud yr aelid, os ym 3-4 o'r ffasb, on dev ops related tasks. Cool. Yeah. So I'm into my sort of Ruby JavaScript. I'm really into my Ember. I use it on any personal projects. Scala and I'm really into my Rust as well. So I'm going to talk to you about Docker and specifically using Docker and Docker Compose to build fairly self-contained development environments. It's something I've done for the SkyGo site because we have a lot of components, a lot of mocked APIs. So it really helps to kind of build these sort of containerized little mini applications, package them all up into a single Ubuntu server, just for development purposes. So Docker is... Sorry. I'm really nervous. So I think before we can talk about what Docker is because it's this giant tool built around a very simple concept which is a Linux container. And so a Linux container is just an isolated section of... It's essentially it's a virtual environment whereas with a virtual machine, you've got a whole sort of the machine as the environment, this... It's like a sort of change route, but even more powerful than that, it's the ability to sort of be able to run, change the sort of base file system, essentially changing the base file system without changing any of the actual file system. So you could spin up a Linux container or spin up two Linux containers on a Ubuntu server. You could completely wipe out the entire root of the one and that state of that Linux container will remain like that. If you went into the second container, it would still be intact. So even though it's changed in one, it hasn't technically changed in the other and changes you do in the other will never be reflected in the first one. So what is Docker? So Docker is essentially an isolated container for your application. So if I had, as I'll show in a short while, an Ember application, I could spin that up into its own single container. I could then spin up my Rails application into a container next to it, even though they'd share the same underlying sort of operating system. They are completely separate of each other and they can technically only talk through sort of host names or ports. So I mean the idea of Docker is to be able to sort of create this environment where you just configure your application once. You can push that up to a remote repository and pull it down, so it's kind of a configure once and run anywhere and you can spin it up multiple times on the same machine or sort of multiple times on many machines. So yeah, so I think one of the main benefits for me in using this approach is it keeps my development environment as close to my production environment as possible, which you can do through a tool like VirtualBox with Vagrant, but that would require spinning up multiple Vagrant machines, which is a waste of resources on your development machine. Yeah, I mean that's sort of a small amount of what Docker does. It does a hell of a lot more. It's a really, really bloated tool and yeah, I wouldn't have time to go into everything it does in a single presentation. So yeah, this is a really good image. Kind of shows you the difference on the left. You've got a standard sort of virtual machine environment and on the right you've got the Docker environment. So I think in this case, the hypervisor would be your virtual machine manager, so VirtualBox or VMware, whatever you're choosing. And yeah, there is essentially only one OS. Yeah, the Docker engine is running on, so you don't have to have multiple guest operating systems installed. You can do everything with one. So then we've got Docker files. So these are what you would use to configure your application. So it's a really simple API. You get sort of a from, run, add, work directory command. So from would be saying what you want your Docker file to inherit from. So you could sort of pick any Docker files from the Docker hub and then you can run your own commands then. Within that, set up your working directory and then the command is generally the last thing you would run in your Docker file for spinning up your application. I've got a small example. So this, yeah, I had to cut it down because it kept resizing the text, but essentially this one would import a base image from IOJS. We'd be able to run our MPM commands to get Bower and Ember CLI. And then you could, there would be some more bits in the middle where you were setting up your working directory or setting up your Ember app completely from scratch. And then you just run Ember server and that will spin up that container and run your Ember application. So then there's another tool which Docker recently bought called FIG and renamed it to Docker compose, which is what I've actually worked with more so than Docker just on its own. And it's a tool for orchestrating multiple applications. So whereas before you would build each one individually, this gives you a tool for defining the structure of your application. So pulling in various, you could have your Redis server or your MySQL server. You'd have another section for your application stack. So, yeah, this Docker compose file is just a simple YAML file. You'll get similar commands in your YAML file to that of your Docker file. So that's another example there, which I'll be going into a little more depth in a few minutes. So, yeah, again, I've just named it Web. You give it a build directory if it's going to be built from a Docker file. So then that will just go into that file, look for a Docker file and build that image out, set up some port forwarding to your machine. And, yeah, then any volumes and where you would like them to sit on that machine. Again, I will go into a bit more detail in a few minutes. So, yeah, Macs and Windows can't actually run Docker natively. So one of the most popular solutions seems to be this boot to Docker, which is really good. It's good for playing around with Docker and compose. It's next to useless for Ember applications. I don't know why there's something to do with the file system on this boot to Docker. It just doesn't handle changes very well. So if you run the Ember serve command within that, it'll appear to work, but you'll find that slowly but surely your memory on your machine is disappearing and you can take up to getting up towards a minute between you changing a file to that coming back through to live reload to actually show you that the file has changed or that it's built it and pushed it back through. So, yeah, my preferred solution for getting around this is just to use Vagrant. Vagrant is an awesome tool. There's a plugin for Docker compose, and there's so many images out there of Ubuntu, which is what we use at Sky, where you can just have Docker pre-installed on that. And, yeah, just get that up and run in super quick. So I will try and make this file size a little bigger. Can anyone kind of see that? Cool, so, yeah, awesome. Cool, so this is just a really simple sort of Docker compose file for setting up a very basic Ember rails and Postgres, sort of kind of a classic sort of Ember application. So this is just going to go off this build command. It's going to go off into applications client. It's going to look for a Docker file, build that from there. I'm exposing ports for 200, as you'll all be familiar with, but also 35729, which will be the live reload one. And then what this is doing here is just essentially sim-linking my applications client into a slash app on the Docker container. And then similarly for the API, which is a Rails-based application, it's going to go off, look for a Docker file inside of that API folder. I've got the commands here, but they're also in the Docker file. Technically, I don't need them here. It's good practice to anyway because chances are your Docker file would be your production build of the actual container. Whereas with this, because it's more fig or compose, it's more of a developer environment tool and not really production ready yet. You kind of re-specify running things into a development mode within fig. It's exposing port 3000. This links is quite an interesting one. Because I've got this db image down here, and I've used image here, this is going to go off to the Docker hub and pull the official Postgres 9.3 image for me. If you wanted the latest, you could literally just do that. I wouldn't do that because it takes probably about 10 minutes to download and configure that, and I've already got a copy locally. It's just going to expose yet again, just exposing that onto 5432. Only one port here because I don't need the port exposed on my local machine. Plus I don't think it'll work because I've also got Postgres on my local machine running. The same here with volumes. This links, because I've got that db down there, that is going to create a host name then on my API Docker container. In my database.yaml file, I can literally just reference db as the host name and it knows exactly where to go and pick that up. Again volumes, this time just specifying the API and again to the slash app. Even though these will both be running on the same Ubuntu image and both be running from slash app, they'll be completely self-contained. The Rails 1 won't be able to see the files of the Ember 1 and vice versa. Does FIG allow for orchestration across machines? Or is it just for figuring a single machine? For orchestration across machines, I think they've got a tool called Swarm, which is for doing multiple machines. FIG was just an open source project. It started by some people who just wanted a way to configure sort of more of an application structure over just an individual container. So yeah, fairly simple, vagrant setup. It's just going to use my VM box here, expose a port for me and then we've just got this provisioner, which is Docker compose and run always. I've taken rebuild true off for this because otherwise it's going to destroy the containers and the links to the cached version of my containers, which means you would have to re-download a version of Postgres and just sort of the iojs 1 and the Ruby 1. So we'll take a quick look then. Start with the Ember 1. So inside of here I have a Dockerfile. This is just a brand new install of Ember CLI. The only difference is I've added this Dockerfile in here. So this is going to pull the iojs 2.0 image. Yep, fairly explanatory these two. Yep, going to create our slash app directory. Add all the files from this into that app directory. Set it as the working directory and then install the Ember application. Again, this sort of Ember server command is in here but it is just going to get overridden by the serve command within the Docker compose file. Why is the Ember server invoked in command rather than run? Because it should be the last thing in the file that runs. I don't know the exact reasons. So the command in the server of the box is trying to figure out why it's not just another run line. What? Run happens when you build the image. Every Dockerfile will end with a command. It's curious that it's not like why didn't it run as well and not just a regular shell command reasons. I've never understood that. The idea would be that all the other commands would just be you do that once and it would be getting the machine ready of which that first line is critical step. Most of the work is done for you. You take an image and you set it up the way you want it to set up and that's cached and you never deal that again. I've never actually used Docker in production. I might say. I've used Docker compose in production even though it says not to. But that was literally just for setting up our CI tools in SkyGo. So because we wanted... So we had a Go server. So that's the Fortworks Go server. But we have multiple agents. It just made sense just to have one image for the Go server. One image for the Go agent. And then we can just do scale on the agents. So we can bring up... I think we've got five agents running at the moment. But it's all contained on a single. One thing I was going to ask in this... If you wanted to do further questions later, I'm totally fine with that. But you made this reference to the fact that it's a distinction between testing and production. To me, one of the real promises that a Docker rules is this ability to create an environment which mimics that your test environment is precisely the same. It's not precisely, but as close as possible to the same. But is that... What do you see as being different? You may have come earlier, but you didn't understand what would be different in production. You'd run it differently in production. With regards to this command, I can't remember exactly what I said. I was shaking. So I'm trying to think. So this command is just going to override the command on the actual Dockerfile. So in the Dockerfile you would probably make that environment more production-like whether that's doing your minify in your assets or running it in production mode for a Rails application within your thick or compose file because it's a development environment. You just override that. So you still build pretty much the same environment. The command you're running the application with then is different. So, yeah, probably worth getting this thing running. So inside of here now, you should be able to literally run it up. It's all standard vagrant stuff. Probably worth just a quick... So the only other thing I would have done on here would have been... Yep. So probably worth just noting that that DB link that I set up in the compose file means in your host, in your Rails application you can just call DB. Just adds that to ECT hosts. Just quite handy. Yep, it's all red. That's good for some reason. Cool. So that's the Ember application up and running. Yep. So we have our Rails application up and running. Yeah, I think the benefit of this way over the Boot2Docker way is that I can literally should be able to change. That's strange. It's not running properly. Yes, yeah. So you should be able to... Everything's sort of simlinked in to the vagrant box. So you should be able to do all your... This virtual box used to be kind of slow in terms of the shared file system. It was one of the advantages that VMware had over it. Yeah, it's not as fast as doing it natively. To be honest, I don't really notice a problem with our Angular app, especially. There doesn't seem to be much of a delay. Angular slow. Yeah, terrible. Why did I decide to do this? Yeah, so for some reason this isn't working now. This might be... I'm going to give it a go. How long do you think this will take? No time at all. It was working earlier when I was using it. I don't think I've changed anything. Anyway, that was pretty much... Yeah, should we do some Q&A while the app works? Yeah. We've got quite a bit of time, I reckon. So if you didn't get to go and find out that you could do post-press running inside of... Yes. What happens to the data in post-press? Can you stop the data? The data will still be in there as long as you don't recreate... Yeah, so Docker compose... When you do an up in Docker compose, it's different to an up in Docker in that it will recreate the image. So it's generally a no-go. It'll destroy all the data. But you can start a stopped container with just Docker compose, start, and that'll bring up those containers. I think this is still a recommendation, but the recommendation used to be that you'd also have your state, your database files or storage, would be its own Docker container separate from the actual running instance. So they'd be linked up, and it'll allow you to bring down one version of the database, bring up another version of the database against the same Docker image... Docker image protection has the data. It doesn't have to run anything to be accessed through multiple... Yeah. And you can simlink those as well, those images. So the volume of the database would be on the local files? You can do multiple shared folders in compose. Yes. The container management for OSS is not... I mean, you use Baber just to get to the two basic units through this fully supports. Oh, yeah. If it's in the same folder with your compose file, then it'll already be shared from inside your compose. So if you mapped the data folder that was inside the directory that had the compose, that automatically gets shared because it'll be off slash vagrant inside the vagrant machine, and then the path just seemed to work out relative when it starts up. So it'll go into the machine startup Docker compose inside a vagrant but inside of that... inside of that folder. So then... they do map up. So as much as I want to see this working, I think in order to get to the music, I'm going to have to go off of your pause right there. Cool.