 Awesome. Well, thank you everyone for being here. This is the CICD 101 workshop. I am, in case you all had signed up previously a long time ago, I am filling in for another representative at CircleCI. His name is Angel. He was not able to make it today, so I am filling in in his place. My name is Michael. I am a solutions engineer with CircleCI. Basically, it's my job to work on the presale side of the sales process. I help educate about CICD as well as promote and discuss our product, CircleCI. However, I want to make it clear that although I am a representative at CircleCI and I am using CircleCI in this demo, because that's obviously what I'm most familiar with, this is not specifically a workshop to promote our product, if that makes sense. Just so you all know. On the agenda today, I wanted to discuss some CICD basics as well as some common pitfalls and mistakes that people fall into when discussing CICD. Then I'd like to open this up for a bit of a discussion. I'd like to talk to all of you what you are doing today for your testing and deployment processes. I'm going to discuss some common terms and concepts that you will find in common between all CICD products and tools and vendors out there. And then as time allows, we'll try to get through using CircleCI and getting your first screen build as much as possible so that you can get hands on what it's like to put together one of these pipelines for a project. And I've got a demo project ready for that, so you don't have to put on your own project or anything. You'll be able to clone this project. And then finally we'll end with questions and next steps. Any questions or concerns before we get started? Cool. And also just a really quick gauge. How many of you are already familiar with CICD to a certain degree? Okay, so you are pretty familiar with it. I won't go into too much detail on these beginning slides then. So as you all know, the IT industry and software in general is booming. Tons of startups are popping up all over the place. This summer actually was the second year in a row that Y Combinator, on Hacker News, they just did a startup school this summer or something like that and there's like some 24,000 startups that are participating in that thing. So companies popping up all over the place and tons of companies, big companies, or corporations that you've all likely heard of, they are all doing huge IT tech transformation, etc. And so what rapidly growing industry means is that you've got rapidly growing teams and if you've got rapidly growing teams you've also got rapidly changing code. And this is in particular problematic because what happens is that with all of this constantly changing code, it gets harder to track, it gets harder to maintain, it gets harder to really merge in those changes and whatnot and you can introduce lots of problems and lots of hiccups in your development process and deployment process for any new applications you roll out. So the industry's response to this is something called CI CD. CI is continuous integration and continuous integration is the constant integration of changing code into the main code base. Developers are making code changes often. You run automated tests to validate those code changes and make sure that they didn't break anything and then only actual passing changes, changes that passed all the tests, are accepted and merged into the main code base. So what this means is that you have a main stable branch that always has the latest features and bug fixes and you can reasonably expect someone on your team to clone your main branch and it will be stable and not broken. Continuous delivery is along the same lines but on the delivery side of things. You are constantly delivering that changed code. Deployments are automatically triggered after these tests are passed and then what this means for you is faster release cycles. After you've tested these changes and then you've verified that they're working, you can immediately deploy your new application without any hiccups that you would typically take because all of the things that I'm talking about right here are things that people used to take weeks, months to do, right? After you've deployed your application or after you've pushed your changes to GitHub, you've got this whole QA team that has to run through this giant suite of tests that they check off on Excel. People are automating all that now and after running all those tests you've got a whole operations team that's responsible for spinning up infrastructure, deploying the application, testing these to make sure they work. Again, all of that is being automated now and so with these more automated release cycles you can do more complex deliveries. You can do blue-green deployments, you can do canary deployments, etc. And then what this means for your teams is that by automating all this you can deliver consistently, save time and reduce errors along the way. CICD together culminates in essentially main principles which are number one, fail fast. If there is a problem you discover it sooner, you can deal with it quicker, you can easily find and fix these issues, test them again and then run through these and then merge that stable code into your main branch because you're doing it all of this automatically. And then after that you automatically deploy that latest code with the latest changes and all of this culminates in delivering stable apps consistently and quickly which means more productivity for your team and ultimately more money for your company, ideally. That's the goal. So along those same lines there are some common pitfalls and mistakes that people fall into when discussing CICD, right? And the first one is believing that cheaper is better. Now I can understand why this would be a mindset that people fall into because ultimately what you're doing by implementing CICD is by cutting costs, right? And those costs might be, oh, you know, I don't want to... Mistakes in production and deployment can be very expensive and so CICD is in a way meant to be helping reduce those costs. However, what that also ends up being translated to is teams like to consider tools that are free. For example Jenkins, right now today you can download Jenkins for free and you can install it on your own infrastructure and then run your own CICD pipeline. However, that's a little bit short-sighted. I think Jenkins is great. Jenkins has been around for a long time and is really a forefather to the CICD movement in my opinion. However, the thing about Jenkins is that although it's open source and free, you get to deal with and manage everything yourself, okay? You get to get your own infrastructure, you get to install Jenkins yourself, you get to manage all the plugins, configure all the repositories, configure the web posts, configure the authentication, et cetera. You get to do all that yourself and whenever there are problems, you also get to fix them yourself as well, right? And so cheaper is not necessarily better. Sometimes it's worth it to spend money and to use the SaaS applications where everyone else is doing the heavy lifting and doing the crap work for you, if that makes sense. Why manage your own infrastructure if you don't need to? This is also part of the same thinking behind why people are migrating over to cloud, okay? Why would I want to deal with thousands of my own servers when Amazon or Google can do that for me? Same principles here. The second mistake people have is not having a budget. Along the same lines, once you've kind of gotten over the hurdle of really wanting everything to be free, you then need to really set down a budget that you have for this project. And really you should be doing this for every project you pick up. You want to have a budget. When you have a budget, you can strictly define exactly how much money you're willing to spend and kind of we'll go over it later, but if you have a budget then you can also start to assess the amount of value you can derive from picking up this tool, okay? No budget means you don't have a value defined for CICD. That's like jumping into doing something without really having an end goal in mind. It might be fun, but it's also a lot of wasted money and time. And along similar lines, that's a little bit worse than not having a budget is not having CICD at all. If you're not automating your tests and automating your deployments you're probably starting to fall behind at this point in the industry. Most of these software teams are delivering tons and tons of applications, tons of changes and fixes to the code. And I can tell you right now that they are not testing manually and they are not having big operations teams all devote a whole week or two weeks that just deploy this application. Everything happens automatically in pipelines now so that their developers and engineers can focus on the stuff that really matters, i.e. site reliability, actually engineering and develop applications, insights, analytics, etc. The stuff that you can actually gain and derive intelligence and value from rather than the busy work of getting things up and running. Some more pitfalls that people fall into, not having metrics. Again, in order to really derive true value from picking up and adopting any kind of tool in your tool chain, you have to have metrics to help you decide and figure out whether or not you're really gaining value from picking up this tool. Different companies and different organizations will have different metrics to determine how valuable a certain tool or a certain paradigm is, whatever it is for you, you need to sit down with your team and figure it out. It could be number of releases per sprint or per cycle, number of commits, number of issues crossed off on JIRA, whatever it is, you need to figure out what those metrics are and then compare those metrics before and after the adoption of new tools to really decide if adopting this new tool has improved your team's productivity and was worth the money spent on it. And then finally, the last one is not having a plan of attack. Kind of like when you go into a new project, you kind of want to have an end goal in mind so that you can really say for sure whether or not you were successful. Along those same lines, because CICD is such a fast, expansive thing, you could automate practically everything in your tool chain, every single project that your company works on, which could range from just a couple to several thousand, right? If you're picking up a new tool and in your chain, then you want to really get the best bang for your buck. And so what you're going to want is you're going to want to spend time automating the most valuable items first and not the least valuable items or tasks. Sometimes companies who enter the CICD space and pick up new tools in their chain, they don't really spend time thinking about this and what they end up doing is while they learn a lot about the tool and they end up automating some things, they're not automating the most valuable things. And that might have an effect on what their opinion is of the tool before they adopt it. Any questions or concerns about anything we've talked about thus far? Yeah, in the back. What do you say is the best open source CI solution? The best open source CI solution. That's a tough question. The word best is very subjective, right? Because it really depends on what you're after. A lot of open source CI solutions, because they're open source, what happens is that the logic or the application itself is provided for free but then you get to manage the infrastructure and everything else surrounding it by yourself, as I mentioned at the beginning. As for which of the tools is best for that, I'm not really sure. Some open source tools that I've heard of are obviously number one Jenkins. Jenkins is probably predominantly the winner in the open source, the ICD space. There are some probably less used tools. I've heard of concourse, for example, concourse CI. There's also GoCD. I believe those three are all open source and free. I know Travis CI offers basically free usage for any open source projects. But if you want to run, for example, built on private projects or non-open source tools on your own, then you're going to have to pay for that. So I don't think they're technically considered open source. Other than that, it's hard for me to really give you a clear answer on this one because it depends on what you're looking for and I've only heard of three open source CI tools. There are probably many others out there, but I don't know about them. Any other questions? I'd like to just get a little bit of information from all of you in the audience here. I'd like to hear about what kinds of testing processes or deployment processes that you are currently doing today and whether or not you experience any pain points from them. Is there anybody doing, I don't know, playing web applications here? For example, Java. You might do, okay, got a couple, got some web applications here. Any Java? Any Go? Okay, Java and Go. Node.js. All right, JavaScript. Anybody experimenting with Rust, by any chance? We have some people building Rust projects on our platform. It's actually really cool to see. There's a whole bunch of different projects out there, but any pain points or struggles that you deal with in your processes for testing and deployment? Running ED tests that depend on things like Selenium. Okay, so running tests that depend on Selenium. All right, interesting. So a lot of browser testing then? Okay, browser testing. Specifically, what kinds of pain points are you experiencing around browser testing? In-consistency tests will fail once and succeed a minute later simply because it's always not timeouts or something like that. Okay, inconsistencies and tests because of timeouts. All right. Yeah, that's a common one for sure. Another hard one that I'll pitch in here is if you have like a microservices application or something, it can be really hard to get a good pipeline down for that because now you've got individual components within your application that you have to test individually. And then, of course, you're going to want to test one change to a component and how it affects the entire system, right? Because just because your unit test passed does not mean your integration tests will or your end-to-end tests will. So that's another challenge people run into. All right. Any other input here? Any other interesting things people are doing with their applications? Yeah? It may take like one or two weeks, but long before the pipeline could actually be but the future there seems to be, you know, it can have, like, you know, evidences on that and then it can take like two weeks. So how do you merge that forward and, you know, to make problems and troubles and other options and some options that... because this is a tough situation where you want to really merge that forward to the main stable branch. But that forward is not very good for that. I see. Okay. So I guess, just to reiterate what you were saying, basically you've got lots of different code changes that are happening and you merge that code to a stable branch but you're not ready to deploy necessarily, right? Okay. Okay, gotcha. I mean, it largely... it largely depends on the company's policies and what you end up choosing for yourselves but there are ways to kind of get together cohesive workflow or CICD pipeline for something like that. For example, as you mentioned, like, if you're working on a feature branch, for example, and it's not finished, taking longer than expected, et cetera, then I don't think there's really a necessity to merge that in if it's not ready to be merged. I think the idea of CICD here is to boost productivity and to help automate a lot of the testing and deployment, right? However, that's not to say that you must always be merging in and must always be deploying at regular intervals. I think that defeats the purpose of improving productivity for the sake of consistent releases, which may not necessarily be your team depending on what you're doing. Some companies are able to do this because no matter what, they're always going to have at least a couple bug fixes or a couple features they're delivering with every deployment. But if your company is not like that, if you're not pushing out that many changes that often, it may not make sense to enforce a delivery, for example, every two weeks. Maybe it's erratic, maybe it's sporadic even. I think the original intent of constant or consistent releases is to help increase productivity and deliver more stable code. But if you feel like doing that is actually doing the opposite, then obviously you don't need to. All right. I'll go ahead and move on. So some common terms and concepts that you will find in all CI CD tools, if you will. First is a pipeline or workflow. Circle CI actually uses both of these terms, but you will probably hear the terms workflow and pipeline in many other places. I believe Azure DevOps uses the term pipeline, or Azure Pipelines is actually a different thing, isn't it? Never mind. I'm making things up. So Jenkins uses pipelines. I know that for sure. Workflow is what Circle CI calls it as, but whatever it is, it's basically a term indicating the overarching architecture of your CI CD process. Inside your pipeline or workflow, you're going to have individual jobs or tasks that are for doing one specific thing inside your pipeline or workflow. This might be something like, oh, run unit tests or run integration tests or generate documents or deploy to AWS or GCP, et cetera. Whatever the job or task is, it's this one big atomic story, if you will, to accomplishing a goal inside your pipeline. Now, the funny thing about the CI CD process here is that there's no specific hard and fast rules as to what a job must do. And likewise, if we go a layer deeper, a job consists of individual steps or scripts or whatever commands you're running to achieve that goal, right? For example, if you're running unit tests, then individual steps inside your unit test job might be, number one, set up the environment, number two, set up the database, migrate the database, seed the database, then kick off the test suite and then do a whole this other stuff. Those are individual scripts or commands. Now, as I was saying before, there are no hard and fast rules as to what you have to do and how you have to separate granularly, and so you need to find what works best for your company and your team. What I found personally is that if you have more granularity, if you separate individual things into individual scripts or steps, it helps you debug things more easily. If you jumble together setting up the database and then seeding the database and then running the test suite all into a single step, it might be a little bit hard to debug, whereas if you separate them into different steps, you can tell exactly which step failed. Oh, it's not that my test failed, it's that I didn't set up the database correctly, et cetera. And so, again, it's just finding whatever works for your team. And then another thing that you'll have to deal with in CI CD tools is the concept of secrets, tokens, or keys. These are essentially configuration parameters that are you don't want hard-coded anywhere and you don't want it just resting in your environment in a file on a hard disk, right? And so what you do is you abstract this configuration from the build and it's only inserted at runtime. Every CI CD tool needs to have this concept in some degree, otherwise it makes it inherently insecure. All right? And so those are some of the common concepts and terms that you will run into between all of the different various CI CD providers. Any questions here? All right. So really quickly, that brings us to CircleCI. It's the company that I work for in case you didn't know yet. So CircleCI is a SaaS tool. We are running in the cloud and we manage all the infrastructure for you. Alongside being Docker-native, meaning you can run all of your builds and commands in Docker images as well as build Docker images to deploy, we also offer test parallelization, which means you can take a suite of tests that you have and split them and run them in parallel between multiple containers at the same time. This helps you cut down the amount of time it takes to finish your tests. We have one customer who was able to migrate from another CI CD provider to our platform and between using all of the advanced features as well as the test parallelization, they cut down their test suite and deployment steps from about two hours-ish to down to 20 minutes or so. I can't mention their names even if I'd like to, but that's just an example that I always like to pull out because they're pretty cool. I think they run a suite of some 20,000 unit tests and integration tests or something like that. I think we have a really clean and intuitive UI. People have always mentioned that they like how we separate the output, my steps and commands. It's very easy to get to the information that you care about immediately, and then all of our functionality is built in. So unlike some other CI CD providers who use plug-in architecture, basically, if you want to do this, you've got to install that plug-in. If you want to do that, you've got to install that plug-in, etc. All of our functionality is built in. And so what that means is that you don't have to deal with any kind of inconsistencies between a third-party plug-in versus the main server. You don't have to deal with waiting for somebody to update this one other thing in order for your whole pipeline to work. All of our functionality is built in. And we have a list of various other features as well, but if you're interested in that, you can always visit our website's documentation just like any other CI CD provider. We sit in the middle in the orchestration step of your process, okay? At the very beginning here, you're working on your application, you're developing, and then you're pushing your code. As of right now, CircleCI supports GitHub and Bitbucket. And so what happens is that in the future, however, we are planning on supporting a concept of VCS agnosticism. And what that would mean is that you can use any version-controlled service provider you want to as long as it uses Git. Whether we're planning on supporting other version-controlled systems, aside from Git, like Subversion and Mercurial, I am unsure, but the one thing I do know for sure is that we plan to support other version-controlled service providers as long as they use Git. In the middle here, we are, we and other CI CD tools like us are taking care of the build, test, and delivery portion of your pipeline. There are tons of different things that we integrate with. We essentially integrate with anything that has an API, really. And so you've got various customers doing builds or browser testing with Sauce Labs, where they're doing code coverage checks, they're uploading documentation to AWS, GCP Azure, et cetera. There's tons of different things that they do. And then finally, the logistics, as I kind of just mentioned a little bit, we have people deploying to various different cloud providers or even deploying to their own internal infrastructure using different tools like Ansible, Sol, Chef, et cetera. We kind of sit in the middle here, handling kind of the orchestration of all that logic. Any questions? So for this workshop portion, it seems like a lot of you don't have laptops, and so I'll kind of just walk through some of these things. No need to necessarily participate or anything like that. But if you want to follow along with this workshop, you can. All you basically need is a text editor, Git, your brain, and actually a GitHub account. That's what I... All right. All righty. So the link that you see up here above, if you go to github.com slash mvxt slash ci dash cd dash 101 dash workshop, you will see an example repository that I put together. It is a very, very simple project. It's a Node.js project, and it actually really doesn't even need a Node.js aspect in there. The Node.js aspect in there is primarily for running the suite of tests that I've written for this website, if you will. Really, the actual project itself is just a bunch of static website files, and so technically speaking, you could deploy this and do a whole bunch of stuff with it without Node.js even being present. So in defining your pipeline, essentially one of the most important things you're going to want to do is you're going to want to define this, you want to achieve in the pipeline. So, I'm going to whip up my notes here and we're going to define exactly what we want to do. Is that text readable on your chance? Is that text too small? Okay. One second here, see if I can even do that. Is that big enough? No. Is that big enough? Cool. Alright. So, what do we want to do with our CI CD pipeline? For this workshop, we'll keep things very simple. I've written a suite of tests inside the repository. I use a library called Test Cafe actually, and all of this is doing is checking the content of certain sections of the website. Very rudimentary and very elementary, but your use case need not be this simple. Alright. So, we're going to want to run Test Suite inside this repository. I've also got a docker file. And so, what I have essentially done here is inside this docker file, I have extended engine X Alpine, and I essentially run a set of steps here to put items inside this docker container so that I can serve these static assets from inside a container. It's totally overkill. You don't need to do this at all. If you really wanted to, you could just deploy static website files straight to AWS S3 or any other any other clock provider where you can serve content, right? So the docker container is totally overkill. But, the reason I'm doing this is to demonstrate that hey, there are customers who are building actual complex applications in docker containers, and you can do this with our platform. So, I'm going to want to build the docker container and presumably push the docker container as well. And just for simplicity and ease, I'm going to push the docker container to docker hub because it's free and easy to set up. There you go. All right. Does this make sense? Does this look good? Cool. All right. So, the first thing you end up doing inside your CICD 101 workshop here is if you're following along, the first thing you're going to want to do is you're going to want to fork this repository so that you can have it in your own GitHub account. Assuming you've already done this, the first thing we're going to do is we're going to create a new file. At the top level, different CICD providers are going to do different things, right? They're going to require different files of different names or different folders for this. With CircleCI, you're going to create a folder called .CircleCI and inside the .CircleCI folder, you're going to create a config.yaml. Cool. Inside the config.yaml, what we are going to do first is we're going to start by defining workflows. Workflow, again, is the overarching architecture of what you want your CICD pipeline to do. We recommend that you always define your pipeline first whenever you're working with any CICD tool because you want to know exactly everything that's happening. If it's at the top of your file, then you know where to find it and you can get a big picture of everything that's happening. We're going to do a workflows. Actually, let me do this. Flows. Version 2. Version 2 is just for our platform specifically. We're on version 2 of our workflows right now and jobs. Actually, build deploy. I'm going to define a workflow called test deploy. You can call it whatever you want. And inside this test deploy, I am going to run a test job. All right. Looks simple enough, right? We got a pipeline or a workflow that has one job in it called test. We continue here. We're going to do job definitions. After we define our workflow, we're going to obviously have to define the job that we want to run inside that workflow. So for this, we're going to do 2.1. Version 2.1 here is the version of our config. Again, this is going to vary depending on which CICD provider you use. But CircleCI is on version 2.1 right now. We've added various convenient features and functions and different config things that you could do. They're really nice for writing configuration. So we're at version 2.1 right now. In my jobs, I'm going to define a test job. Typically, in a CICD provider, you're going to want to define the execution environment. Different platforms do this in different ways. In CircleCI, you have a choice between a docker executor, which is any docker image. You want to execute your steps in. You also have the choice of machine executor, which is a whole Linux virtual machine. MacOS executor for Mac machines for Mac builds and iOS builds. And then finally, just a few weeks ago, actually, we rolled out Windows support. And so now you can do Windows builds on CircleCI as well. As of right now, it's Windows Server 2019 with Visual Studio 2019. But inside the environment, you're free to configure and do a whole bunch of work to install whatever software you need for your applications. For this thing today, we're going to do a docker executor. And the image is going to be CircleCI slash node 10. 10.2 browsers. I believe that's correct. Let me double check here, CircleCI. We have CircleCI actually has a bunch of convenience images that we create for people that they can just use. So let's see here. CircleCI docker images. All right, image types. Here you go. So we've got Android, Closure, Elixir, Go, Node.js, OpenJDK, etc. I'm going to go ahead and take a look at the Node.js here. View all available image tags here. So I was looking specifically for 10.15 or something like that. 10.15.1 dash browsers. Yep, I was right. 10.2. Cool. CircleCI Node. All right, awesome. Inside this job, I'm also going to define a working directory and that's going to be home slash CI CD101 workshop here. So by default in CircleCI it will automatically clone your source code into a home slash project folder if you don't define anything. My recommendation to people is to always explicitly know exactly which folder to find all of your source code and items in. And then inside the test job here we define steps. These steps are for doing certain things. We have a built-in we have a built-in keyword called checkout which is essentially just checking out your source code and then we have a basic run step which is a freeform bash command that you can run. So just to make sure everything is working correctly I'm just going to do echo hello world. All right. Add dot circleCI, commit. Then I push this. All right. So now if I go over to circleCI dot com I'm already logged into this application however if you are not logged in you can either click login if you have an account with us already or sign up. Basically what happens is if I just show you here because it's really quick what happens is that you actually sign into circleCI using your github or Bitbucket credentials. So I'm going to login with github here or sign up with github whichever one. I'm going to go to add projects. I am on the wrong group here. Let's see. Here it is. CICD 101 workshop set up project here. I click set up project. I don't need to worry about any of this other stuff. This other stuff is kind of just a little bit of a toil. We've already gone through the work of essentially creating our own little thing here. So we're not going to need to worry about that. We're just going to go ahead and click start building. And that'll kick off the first build of this project here. You can watch it happening in real time. It's spinning up the environment. Also just for verification purposes we have a configuration tab here on our job details page. So you can go into configuration just to verify it is running exactly what you typed in or what you checked in to the repository. Now you can see that it has completed running and is done. So you can see that that was fairly fast, right? That took all of 12 seconds. And that's because we used a docker executor. It's very quick and easy to spin up docker images on our platform. And then essentially the rest of it is just running commands inside the environment. Now, this is great. We've got a green build. But this is useless. It's not doing anything. It's just echoing hello world. So we're going to want to change our code so that it's actually doing something a little bit more important and substantial. We go back into the file here. We see our steps are check out and then run echo hello world, right? So instead of just running echo hello world we're going to want to do something a little bit more important. For example, yarn. I use yarn. Some people prefer NPM where it is. You can run NPM install or yarn, whatever it is. We have a package of JSON inside this project. And so I'm going to use yarn to install the dependencies. I'm also going to modify this slightly. I'm going to change this to name install dependencies and then the command is going to be yarn. And this is just to increase readability. You could just have the run command by itself followed by the command. But I like to include the name and the command in there just so it's more readable. After we install the dependencies, we're then going to actually run the tests. And the command for that is going to be yarn test. Cool. All right, add test commands push and it looks like it's then committing. Now we wait for the next job to kick off. There you go. Now you can see here that what I'm doing here is one of the reasons why people enjoy CircleCI as a platform. Shameless plug here. And that is because it is very quick and easy to make updates to your configuration and then immediately see things running. It's a little bit harder to do this on some other platforms. It might take longer for an environment to spin up. It might be a little bit more difficult to inherently see what's happening inside the environment, etc. With CircleCI it's very quick and easy to make changes to your config file, push it and then see what's running live. All right, you can see here we are installing the dependencies. This is going to take a little bit of time. I don't think we have too many dependencies here, but it's going to take a few seconds. So this is a Node.js project and so we're installing whatever is mentioned inside the package.json. We have various other customers who are doing dependency installation for tons of other languages and frameworks. For example, we have people doing Python, Django or Flask builds and so they're installing dependencies with pip. We have people who are installing Maven dependencies, Gradle dependencies for Java. We have people installing RubyGems to run the Ruby projects. We have people installing whatever it is they need to for whatever languages they're testing with their frameworks. So you can see here that this is actually doing something real and substantial now. We have installed the dependencies that we need for this container and we are now running tests for this project. And so now I can essentially do anything inside the project. This is going to be a bogus change. Class is equal to nav item and then I can just say a class is equal to nav, link, js, scroll, trigger hyperref and then we're just going to call this something. And then add like a something link and if I add this and push it now once I've set up this pipeline it will always run the same steps that I've defined before. And so after I push my new changes here you can see a new job kick off on CircleCI and it is running the same set of tests against my new change that I just introduced here. Now the change that I introduced shouldn't break anything. I don't think fingers crossed. But we'll be able to find out much more easily because we've got this pipeline set up. And so what you're seeing here is really an end goal of using and picking up any CI CD tool and writing out these pipelines is that you want to be able to run whatever it is that you run against your application. Do all these tasks whenever developers make changes to the code base. And this helps increase your productivity because you can always know when someone has committed breaking code, whenever someone has made changes that do something weird with the system or do something weird with your code, etc. And so this ultimately helps your developers be more productive because it helps them figure out what the problems are sooner so that they can address them. There you go. You can see here things are running again and it's running the test suite of my changes. Any questions or comments or anything else about what you've seen so far? Yeah, what's up? We have a job for this project for Master Branch. Does this system store some kind of open links for future branches or something? Okay, so the question is I'm running these builds in the Master Branch. Does our system support doing things in different branches? And the answer to that is yes. I'm not demonstrating that in this demo purely because of the fact that this project is so simple and doesn't really have anything else going on. But yeah, our configuration does allow the filtering by branches. We have lots of different customers who are, for example, they only want to run certain jobs on certain branches. For example, you only want to run a deploy branch on Master. You only want to run nightly builds on the develop branch, which is the branch that's changing every day. And we have ignoring branches by filters as well as by tags as well. You can also do certain jobs and run certain workflows only based on tags. And we have some customers who, for example, use this functionality by saying, hey, we actually don't even deploy from Master Branch necessarily. We only deploy whenever we release a new tag or we push new tags up to our repository. And so that would be the functionality there. Any other questions? We get on time? When does this thing end? Okay, so I'm glad that we got through this first portion of it. It looks like we're running out of time here. And so this is kind of just like the first step that we got through in terms of this workshop. There were more things that I was going to cover. But since we don't have time for that, what I will do is sometime later today I will finish updating the tutorial section of the Read Me on this repository. And so when that update is made, you will be able to see more steps and more of the things that you could do on our platform as well as associated resource files and documentation on it as well. Other than that, yeah, I hope you get a little bit of something out of this workshop regarding CICD. Most of the stuff that you've seen today is stuff that you will find and understand now on most CICD platforms. It's just some small variations here and there in configuration and then different features. Ultimately, what will separate different CICD providers and tools from each other are, number one, the features and functionalities they offer as well as the experience that people have while using the tool. Keeping all that in mind, definitely define metrics and define goals whenever you're adopting new tools. You'll be able to decide for yourself and your team which tool you want to adopt in your tool chain. Thank you.