Ansible From Beginner to Advanced | Andrei Balint | Skillshare

Playback Speed


1.0x


  • 0.5x
  • 0.75x
  • 1x (Normal)
  • 1.25x
  • 1.5x
  • 1.75x
  • 2x

Ansible From Beginner to Advanced

teacher avatar Andrei Balint

Watch this class and thousands more

Get unlimited access to every class
Taught by industry leaders & working professionals
Topics include illustration, design, photography, and more

Watch this class and thousands more

Get unlimited access to every class
Taught by industry leaders & working professionals
Topics include illustration, design, photography, and more

Lessons in This Class

    • 1.

      Course Introduction

      1:54

    • 2.

      Lab Setup

      8:19

    • 3.

      Ansible Inventories

      4:31

    • 4.

      Ansible Configuration Files

      7:50

    • 5.

      Ansible Ad-Hoc Commands

      10:27

    • 6.

      Ansible Playbooks

      17:16

    • 7.

      Ansible Variables

      16:42

    • 8.

      Ansible Loops

      6:02

    • 9.

      Ansible Conditionals

      9:59

    • 10.

      Ansible Templates

      9:27

    • 11.

      Importing Playbooks And Tasks

      15:08

    • 12.

      Targeting Hosts

      4:53

    • 13.

      Ansible Roles

      7:30

    • 14.

      Ansible Galaxy

      8:52

    • 15.

      Managing Users

      6:43

    • 16.

      Managing Services

      3:55

    • 17.

      Managing Storage

      4:43

    • 18.

      Managing Networks

      6:37

    • 19.

      Patch Management

      7:12

    • 20.

      Important Ansible Modules

      38:50

  • --
  • Beginner level
  • Intermediate level
  • Advanced level
  • All levels

Community Generated

The level is determined by a majority opinion of students who have reviewed this class. The teacher's recommendation is shown until at least 5 student responses are collected.

128

Students

--

Project

About This Class

Learn Ansible and also pass your RHCE certification with this highly practical Ansible Course.

Ansible is a very good choice for IT automation because it allows you to specify the desired state of your system and make it so

In this course you will learn foundational knowledge to quickly configure the most important things using Ansible

This professional video course aims to help you master Ansible while tackling and learning multiple topics. 

This is a focused course designed to rapidly get you up to speed on using Ansible automation engine in real life. As an IT professional, you'll develop a solid understanding of Ansible and will be able to apply it to daily automation and configuration management tasks.

This course includes lots of examples and hands-on labs and aims at providing students with first-hand experience with course concepts. You can follow along the course by setting up your own lab environment.

Each lecture introduces a new Ansible concept. Concepts are first explained, and then relevant examples are provided and finally put into practice using the lab environment

By the end of this course you'll be prepared to move beyond manually configuring applications, servers, networks, etc. Beyond writing confusing scripts. To spending your time on more valuable endeavors.

This course also serves a very good learning material to help you in passing your RHCE certification

Meet Your Teacher

Level: Beginner

Class Ratings

Expectations Met?
    Exceeded!
  • 0%
  • Yes
  • 0%
  • Somewhat
  • 0%
  • Not really
  • 0%

Why Join Skillshare?

Take award-winning Skillshare Original Classes

Each class has short lessons, hands-on projects

Your membership supports Skillshare teachers

Learn From Anywhere

Take classes on the go with the Skillshare app. Stream or download to watch on the plane, the subway, or wherever you learn best.

Transcripts

1. Course Introduction: Now, for our first video, I would like to give you a very warm welcome to the course. During this course, you will discover almost everything about Ansible and not only that, but you will also be able to put it to good use in automating both security tasks as well as common system administration tasks. But before we do all that, let me tell you a bit about myself. My name is Andre balance. I'm Alexa engineer and they have a teaching experience of over eight years working with large organizations throughout Europe as a trainer. I have experienced in both working with Red Hat Enterprise Linux as well as with Ansible focusing on System Administration and automatization. I also have the certificates to back this up. I'm already certified engineer from a security standpoint, I Income Security Plus certified n mile to CISO certified. So I cover both security as well as automization using Ansible. I'm a perfect fit to be your trainer for this particular course. Firstly, we shall be looking at and what is Ansible and how we can install it. We shall be looking at what are Ansible playbooks and also how to create playbooks and manage them. After we have a baseline understanding of playbooks, we should be looking at variables and loops and how to use variables, loops and conditionals within playbook. Then we will look at ways in which we can reduce the complexity of playbooks through modularity. Afterwards, we will look at Ansible roles, what they are, how can we get them, and how can we use them? Then, before finishing the course, we should be looking at ways in which we can automate administration tasks, both common system administration tasks and security-related tasks. So now that we have a good overview of what we shall be covering, Let's see what are the prerequisites for this course. A good understanding of both Linux and Linux system administration is recommended so that you can follow this course easily. From an asset point of view, you need to machines running Red Hat Enterprise Linux with network connectivity, the machines can be virtual or physical. It just doesn't matter. Now that we have finished with the presentation, Let's get started with the course. Here we go. 2. Lab Setup: Hello and welcome to the automation with Ansible. My name is Andre Belinda. I'm Alexa engineer and they have a teaching experience of over eight years working with large organizations throughout Europe as a trainer. I have experienced in both working with Red Hat Enterprise Linux as well as with Ansible focusing on System Administration and automatization. I also have these certificates to back this up. I am already certified engineer and the redhead certified System Administration. From a security standpoint, I Income Security Plus certified n mile to CISO certified. So I cover both security as well as automization using Ansible. I'm a perfect fit to be your trainer for this particular course. Now that we have finished with the presentation, Let's get started with the course. Here we go. The first video, we shall be talking about what Ansible is and what are its benefits for an organization. So let's get started. So why Ansible? Ansible is used for automating IT tasks such as configuration management, application deployment, and interests, service orchestration and provisioning. Automation is crucial these days with IT environments that too complex and often need to scale too quickly for system administrators and developers to keep up if they had to do everything manually. And simple simplifies complex tasks. Just making developers jobs more manageable, but allowing them to focus attention on other tasks that add value to an organization. In other words, it frees up time and increases efficiency. So what are those characteristics? Well, Ansible is powerful. You can use antibody to automate almost anything. And so well, it's simple through the use of Playbooks, automation becomes easy to work with and understandable for humans. Ansible is agentless. There is no need to install any agent on managed hosts. All modules are passed through OpenSSH or when RM and Ansible is versatile. And Isabelle provides support for Linux, Windows and unix devices running in physical or virtual or Cloud environments. So let's look at the steps for installing ansible on Red Hat Enterprise Linux. You need a valid Reddit automation platform subscription on the control node, on the manage hosts, if they are running Linux, they need to have Python 3.6 or later installed, or Python 2.7 or later installed. You need to enable on the control node, the Ansible repository. Afterwards you can use the yum command to install ansible on the control node. Ansible needs a user in order to connect to the manage host. So you will need to create a user with administrative privileges on the manage hosts to be used by Ansible. And it is best practice to set up also key-based authentication through SSH for that user. Now that we have covered the prerequisites, I would like to show you a diagram of my lab environment. I have the control node connected to a switch with Internet access to the same switch. I have also connected my two managed host name server a, server B. I would like to point out that you can use either physical or virtual machines for this setup. It really doesn't matter. It's up to your individual decision. So let's get started with the demo. In a demo where we shall be installing ansible step-by-step and then testing it. First, I will be using the user add command to create a user called automation on the control node, and also give a password to this user. The password for the user automation shall be uncivil. Now, I will be SSH over to server a to create the same user. I will again use the user add command. To add the automation user. As you can see, the user was added and that we'll be using the paths v d command in order to set the same password. The password will be uncivil. Now, I did mention that this user will need administrative privileges. So I will add him in these two doors dot d folder under the automation file. And I will give him the ability to run all commands as root without requiring any password by putting the following line in the pseudowords dot d folder. Now let's test this. I will switch over to the user automation by using these switches or command. And I will be running a command, sudo privileges, system, CTL status, SSH D. And as we can see, it has run correctly and no password prompt was needed. I'll be exiting this session and doing the same thing for server, be connecting overthrew server be to say SSH, using the user add command to add the user automation, setting the password Ansible for the user automation. And then again, creating a text file in the slash, ETC slash two doors Dadi directory. So that I can give the user automation administrative privileges so that you can run the sudo command without needing any password. Now that this is done, I will again test this. I will switch over to the automation user and run again pseudo system CTL status, SSH D. Now ever no password prompt, that means it worked just fine. Now I will exit the session and switch over to the control node. I will check my pseudo files on the control node to see if the user automation can run administrative commands without any password and it is clear that he can. So now I will be switching over to the automation user. I will be using the cd command to go over to the home directory of the automation user, using the SSH key gen command. In order to create an SSH key, I will not use any password or pass phrase for this key. And then I'll be using the SSH copy id command in order to send the key over to server. In order to finalize the key exchange, I will need to input the password for the user automation. And afterwards, as you can see, the keywords added successfully, I terminated by mistake my automation session. I will log in again to the automation user, change directory back to my home directory. And I'll do the same thing for server be SSH copy id server B. I am again prompted for the password, which I will input in order to finalize the key exchange. Well, that was a mistake. It is done. Now let's see if key-based authentication works. I have connected to both server a as well as server B without any password prompt. So everything is good to go. Now let's exit this session and return to the automation user on my control node, I will be running the sudo yum, install ansible command in order to install my Ansible on the control node. And this will take awhile. It has 123 megabytes, so it will take a bit of time. After the installation has been finalized, I can start using Ansible right away. So Yum has solved all dependencies and all the packages were successfully installed. Congratulations. Now before we test this, I would like to show you my slash, ETC slash host files. Well, I have given names to my managed host server a and more respectively, server B. Now, before we run an answer will ad hoc command to test our environment. I would like to show you my inventory file. Now, an inventory file tells Ansible on which host tests are done. It is necessary to have an inventory file or Ansible will not know or which holds the task should be done. As you can see, I have grouped server and server be under the category web servers. Now I will run an ad hoc command using the module ping and the web servers category, specifying the inventory file through d minus i option. Everything is working just fine. Green, green, green. The pink was successful. Congratulations. You have a working and civil infrastructure and a very good lab environment to take us through this course. 3. Ansible Inventories: Now for our first video, we shall talk about ansible inventory files. At the end of this video, you will know what is the purpose of inventory files and how to create and manage them. So what are Ansible inventories? Well, an ansible inventory file defines on which hosts or groups of host commands, modules, and tasks in a playbook or ad hoc command are operated on. The inventory file can list individual hosts or user-defined groups of hosts. This enables you to define groups of devices on which to run certain commands. That default location for the inventory file is slash, ETC, slash slash hosts. But you can also create project-specific inventory files in alternate locations, which can be specified either in configuration files, playbooks, or using the minus i option for ad hoc commands. An inventory can be written in either an any format or in YAML format. Let's take a look at a sample inventory file. This specific inventory file is written using the simple INI format within it, you can list host by IP or host name, but you should know there should be only one per line. In order to create a group of hosts, you need to declare the group by using the brackets and fill in decomposition of that group. For group one, we have server, a server be for group two we have server and server. We can also create what is called a nested group by using the children's suffix and specifying these subgroups. I would like to add that you can also use ranges within an inventory file. You can specify both numeric or alphabetic ranges. Let's move on to the demo and see how this is done in practice. So let's start this demo by first creating an inventory file with the VIM inventory command. In this inventory file, I will add some gray. I'll create a group called group one, which will contain server B. I will then create a group called group two, which will contain server a. And then I will create a nested group called group 12, which will contain both group one as well as group two by using the children suffix. Now that I have created these groups, I can exit my inventory. And I will use Ansible ad hoc commands to see if it works. First, I will make Ansible list all hosts within my inventory, specifying the inventory with the minus i option. And we can see server and server b. Then I will make Ansible lists all ungrouped hosts within my inventory. And as you can see, there are no ungrouped hosts because all of them are within groups, either group one, group two, or group 12. Now, I will list all the hosts within group one. We can clearly see that server B is present. And I will do the same thing for group two, ansible group two minus minus list hosts and specifying the inventory with this minus i option. And we can clearly see server a is present there. Now let's see if the nested group is functioning adequately. By listing the hosts within it. We can see both server a, server B, so both group one as well as group two. So it's pretty clear there's my inventory is functioning adequately. Let's just test this by running an ad hoc ping command to all servers within the inventory. We can see that both server, as well as sort of Birkby have responded successfully with a Pong response. And let's do this operation for each individual item within our inventory. First for group one, and see if it works. Specifying the inventory with the minus i option. So cerebral B has responded correctly. Then we shall do the same thing for group two. February has responded successfully. Now let's finish up this demo by clearing the screen and doing the same thing for group 12. As you can see, both server, a server behalf responded by nested group works perfectly. Congratulations. Now you know how to create inventories and manage the host within them. Also. In our next video, we shall be going into Ansible configuration files. See you soon. 4. Ansible Configuration Files: Now we shall look at Ansible configuration files. So without further ado, let's get started. So the way people behave is specified in the Ansible configuration file by default as well, has a configuration file located at special ETC. Slash Ansible, ansible dot CFG, which is used unless another configuration file takes precedence. If an antibody dot c, f, g exists within the home directory of the user running it, it will take precedence over the default configuration file present in slash, ETC. If an Ansible configuration file exists in the working directory, then this will take precedence over the two beforehand. And if the Ansible config variable is defined, then this will take precedence over the three stated above. Settings are not accumulated from multiple configuration files. So anything not stated within the Ansible configuration file will be set to the default value. That default value can be found in the default Ansible configuration file present in slash, ETC, slash n sub l. Now let's make things a bit more practical and look at the sample configuration file. Now, as you can see, the configuration file has sections. These sections are within the square brackets. We have the default section and the privilege escalation section. In the default section, we have the inventory field, which defines the inventory that shall be used. The remote user option specifies the name of the user and sub l shall use to connect to the manage hosts. And the ASP pass option specifies if a password prompt is necessary for connection. Now, let's move on to the privilege escalation section. Now within the privilege escalation section, we have the become option, which means that ansible we'll switch user after the connection has been established. They become method is the way in which it will switch that user. This is set to using sudo. Which user it will switch to is defined by the become user argument. In our case, Ansible will switch to the root user upon connection. They become ask pass argument defines if a password is necessary in order to facilitate and finalize this user switch. So now that we have a pretty good overview of basic but important Ansible configuration file options. Let's go ahead and put them into practice in the demo. So we shall start this demo by making a new directory called configuration file, where we shall create our own personalized Ansible configuration files. We shall use the MK D or command in order to do this. Now before we create our own configuration files, Let's look at the default one stored in slash, ETC slash n sub l. As you can see, this one is also grouped into sections, and we are currently viewing the default section. There are a lot more options than we have learned in the slides, and you can research each and every one should the need arise. These values here also define the default way in which Ansible behaves. Most of the options are explained here using comments, but we have covered the most important ones within the course. As you can see, I'm scrolling down to give you an overview of the multitude of options for customization that ansible offers. So let's exit and create our own configuration file. First, I will use the cd command to change directory back to my configuration file directory. Then I will use the VIM in order to create a file called ansible dot c, f, g. First I will switch into insert mode, and I will specify the default section. Here. I will specify what inventory I would like Ansible to use, specifying the path to my inventory file. In this particular case, the path will be slash home slash automation slash configuration file slash inventory. Then I will begin specifying the remote user that ansible we'll use to connect to the manage host. And this would be the automation user which is present on both server a, server B. Now, when it comes to privilege escalation, I will first specify the specs that section within brackets. And I will say become equals true. That means that upon connection, Ansible will switch user. It will switch the user using the pseudo method, and it will switch to the user root upon connection using sudo. And as there is no need for a password, I will specify that they become ask pass is set to false. Now I will create the inventory called inventory. And here I will specify server a, server B, Save and Exit. And let's try a ping command and Sibyl all minus m pink. As you can see, there is no need to specify the minus i option as the inventory is defined in the Ansible configuration file. Let's try an Ansible or minus m command, minus AID. This will give us the ID under which Ansible is running on the managed hosts. And as we can see, it has a new idea of 0. That means we are running as the root user. So let's edit the Ansible configuration file. I will open it. And I would like to use as my inventory file, a file called inventory too. I will just enter Insert mode or the two at the end, save and exit. And then create a file called inventory to where I will just specify server a, save and exit. And then let's run an Ansible all minus m ping command. And as you can see, only server a responded with punk. So that means it's only using the inventory to file. Let's change the Ansible configuration file again. And let's switch become to the value of false. That means that Ansible will no longer switch users upon connection. And let's test this by running an Ansible or minus m command minus AID. This will give us the idea under which Ansible is running on the managed hosts. So it has a UID of 1001. The user automation no longer looked at. It has not done any privilege escalation. Now that this has worked perfectly, let's try something a bit more interesting. So first, I will copy my configuration file to the home of the automation user using the cp command. And then I will remove my existing configuration file here in the working directory with the remove command. Now, let's try to run the same command again. And as you can see, it says that the provider hosts list is empty. It didn't work. Why is that? That is because I copied it under the name Ansible CFG instead of dot ansible CFG. If it doesn't have the same name as Ansible expect, it will not be taken into account. So let's rename it using the move command M, V Ansible CFG dot ansible dot C, F, G, and see if it works afterwards. Run the command again, and as you can see, it has worked perfectly. Now, let's change the working directory over to configuration file and run the same command. Again. If the output is the same, that means that the configuration file, which I have placed in the home of the user automation is used by Ansible and also takes precedence over the default configuration file present in slash, ETC. We can clearly see that both outputs are identical. And with this, we have finished our demo on configuring and sub L. Now, we shall be moving on with Ansible ad hoc commands in the next video. 5. Ansible Ad-Hoc Commands: In the last video, we learned about Ansible configuration files and now we shall put that to use with Ansible ad hoc command. So let's find out what they are, how to create them, and how to use them. Ansible ad hoc commands are used for single-use task with Ansible, they're usually used for testing certain things or quick changes. Their usefulness is quite limited though. And if you'd like to use the full power of n tuple as an automation engine. You would most likely go for playbooks. Ansible ad hoc commands can make system administration tasks a bit easier and quicker also. So let's see how to construct Ansible ad hoc commands. This is the standard pattern for Ansible ad hoc commands. First, you have to choose the hosts or the group of hosts which the command will target. Then you have to specify the module through d minus m option to that module, you have to attach arguments through d minus a option. Then you have to specify the inventory which Ansible will use with the minus i option. Or if you haven't already existing Ansible configuration file, you will not need that. You can also specify the user which Ansible will use to connect to the managed host through d minus u option. Again, if that is defined in your Ansible configuration file, that will not be necessary. I would like to specify that for the host argument, we can also use the all option, which will target all hosts within the inventory, or the ungrouped option, which will target all ungrouped hosts within that inventory. Now, let's look at some sample answer. Well, ad hoc commands. The first command we have here on the slide, Ansible all minus m ping, ping all hosts within the inventory. The second command, Ansible server a minus m copy minus a content equals HelloWorld, destination slash home slash automation slash hello-world. We'll copy the content Hello World to a file stored at slash home slash automation slash hello-world on server a. The third command, Ansible servers minus m Command Minus a host name, will run the command hostname on the group called servers defined in the inventory. Before it's command. Using the user module, we'll create a user named test on server, be using the inventory specified through d minus i option. The last command, Ansible doc user, will give us information on the user module and how to use it. You can also get this information online if you have an Internet connection. As redd provides pretty good documentation. So now that we've seen some sample Ansible ad hoc commands, Let's look at some modules that we should know through the pink module, we can check host accessibility. Through the user module. We can manage users on the Manage host. Through the service module. We can manage services on the managed host. Through the copy module, we can copy a file to the managed host, but also create content. And through the EU module, we can manage packages on the managed host. Through the file module, we can manage piles on the managed host. Through the firewall d module, we can manage the firewall service on Manage host. Now that you understand what ad hoc commands do, and you've seen some sample ad hoc commands. Let's move on to the demo. Now, I will start off this demo by first creating a directory using the MK dir command. And then three will be called ad hoc lab. I will quickly change to that directory and create an Ansible configuration file. Within this Ansible configuration file, I will first define the default section, where I will specify first my inventory file. And this will be found in slash home slash automation slash ad hoc lab slash inventory. Then I will define the remote user that ansible, we'll use a punk connection and this will be the user automation. Now that I've finished my default section, I will start my privilege escalation section. Here, I will first set D become to the value of true. They become user will be root and they become method will be pseudo. Now they become as pass, I will set it to false as there is no need for a password prompt. I will say my configuration file. And now I will create my inventory using the VIM inventory command. This inventory, I will include both server, a, server be, save and exit. So now let's run a few ad hoc commands using this Ansible configuration file and ansible inventory. I will ping all hosts within the inventory. And as you can see, both server and server B have responded with a Pong response. Ansible server a minus m command minus a for argument host name. This will run the hostname command on February. As we can see, the output is server a. As you might expect, I will use the command module again in order to run the id command on February, and it works perfectly. I'll clear the screen. And run a new command, but this time on server B, I will again use the command module, but this time I will make it output the contents of the slash, ETC slash past VDI file using the cat command. As you can see here, all of the users, including automation, are present. Now, I will create a user using an Ansible ad hoc command with the user module on server, a server a minus m user, and specifying the name of the user and the state in which that users should be on the managed host. In my particular case, state present. I will now click enter. And as you can see, the new user has been created and the UID is equal to 1002. Now, we can also validate this by again checking the past VDI file using the command module and outputting the contents of the slash, ETC slash password file. And we can see the test user with a UID of 1002 and the GID of 1002. Now, if I would like to remove the user, I will just run the same command but with the state equals absent. As you can see, server, it has reported a change. And we shall run again the slash pass VD command in order to see if the user test is present. And you can see it's no longer there, it's absent. Now, let's use the Ansible document for the module user to get more information on how this module works. And we can see what it does, and we can see the options and arguments that it has, like append, authorization, comment, generate, SSH key. Now, I would like to point out everything which has the equals sign means it is compulsory, like name. Everything which has the minus or lines sign is optional, so they do not need to be specified specifically. Now, at the end of this particular Ansible doc for the module user, we will find examples. These examples are extremely useful and they help us quite a lot in understanding how a specific module works and how a specific module functions. As we can see, the examples are easy to understand and easy to decipher. Plus they are commented and say what each example is meant to do. So let's exit. Let's clear the screen using the clear command. And now let's do another ad hoc man on server. Be more specifically using the module copy. We shall create content. And the content will be equal to my test file. And the destination of this content will be equal to slash home slash automation slash test file. Now, I will just hit Enter and from the output of the command, we can see that server B has reported a change status. So let's go ahead and validate our work by using an Ansible ad hoc command with the command module in order to output the contents of the testfile, which we have just created using the copy module. So the bowl server b minus m Command Minus a cat slash home slash automation slash test file. And we can clearly see the my test file content which we added in the previous ad hoc command. So it worked perfectly. Now, I'll just clear the screen using the clear command. Now for our last example, which will restart the firewall, the service on both server and server be using the module called service. I will specify the arguments with the minus a option, the name of the service, which is firewall, the end the state will be set to restart it. That means restart the firewall, the service. I will now hit Enter. And as you can see from the output, the firewall, the service has been restarted. It has been restarted both on server a and also on server b. We will get this type of output for each server. Now before we end this module, let me just clear the screen and use Ansible doc to get some information on the service module, we can find a pretty good description of what the module does. What are mandatory options and what are the compulsory options for this module? And at the end, we will see very good examples on how this module works. Now, I'll just exit the Ansible dogs clear the screen again. And I would like to thank you for joining me in this demo. Now you have a pretty good grasp on how Ansible ad hoc commands work and how we can create them and run them. So I would like to congratulate you upon finishing this demo. We will move on to the next video, Ansible playbooks, where we can see the full power of the Ansible automation language. 6. Ansible Playbooks: We have previously covered inventories, configuration files, and ad hoc commands. So now it's time to move to the bread and butter of Ansible playbooks. So let's not wait and get right to it. So what our playbooks, playbooks are a sequence of plays, a plate being a sequence of tasks performed on manage hosts. The purpose of playbooks is to simplify administrative tasks into easy routines. Tasks can work together within a playbook to document the steps needed to achieve an intended outcome. And best of all, playbooks are repeatable. They can be used more than once to achieve that outcome. Now when it comes to playbooks, they are written in YAML format and saved usually with the extension of dot YAML or that YAML. They use spacing for indentation children more than parents. So keep spacing constant or they will crash. Empty lines do not impact the playbook. The start of a playbook is always three lines and comments can be added using the hash character. Strings do not have to be in quotation marks. It is recommended to use quotation for readability. You can write multiple players within a playbook and tasks are executed in order from top to bottom. If a test fails, then the playbook will stop and no subsequent tasks will be run by default. There are workarounds for this, and we shall see that as we go within the course. Now, when running a playbook, the output will be color-coded. Green means that the system is already at the desired state. Yellow means that a change has been made to the system of the managed host in order to bring it to the desired state. And red means something went wrong and the task could not be finalized or could not be performed. Red is usually bad. Now, with all of this in mind, let's look at the sample playbook. We have the three dashes which signaled the beginning of the playbook. Afterwards we have the name of the play. In this particular case, this play is called create new user. We have the hosts to which this playbook applies. In our particular case, it applies to server a. And then we have the tasks. This signals what tasks will be performed on the managed hosts within this play, each task has a name, uses a module. In our case, the name is ensured that user is created. The module is user. The name of the user which will be created is test, and the state of that user is present. This task ensures that the user test is present on the managed host, which is server. Now, let's take a look at another sample playbook, which contains multiple tasks, the one below dependent on the one above the playbook target server B. And by using the module, it will ensure that the service called firewall is installed on server be afterwards, it will attempt to start the firewall, the service. This is only possible because tests are run in order from top to bottom. You couldn't start the firewall disservice if it did not exist in the first place. Before we move on, I would like to underline the importance of spacing both the first task, the second task, have the same amount of spaces because they're both children of the task section. Inadequate spacing can lead to the crash of a playbook. Now, before we move on to demo, I would like to tell that you can customize some configuration options for individual playbooks. You can specify options which will take precedence over the ones present in the Ansible configuration file. You can specify the remote user Ansible uses to connect to the manage host. You can specify the user Ansible switches two, and you can also specify the way Ansible switches to that user. In order to run a playbook, you just need to run the Ansible playbook command and specify the name of the playbook. If you'd like to check the playbook before running it, you can either do a syntax check by using d minus minus syntax check option or running a dry run through d minus uppercase C option. So let, we have a pretty good idea of how playbooks work. Let's go ahead and start the demo. Now first, in order to make writing plague books a bit easier, I'll create a file called dot v Marcy in my home directory. This will ensure that whenever I press tab the spacing will be constant. So I should write here auto cmd file type YAML, because all playbooks will be in YAML format. Set local Ai equals two, S w equals to e t. I'll just save and exit. Now whenever I create a YAML file, the spacing will be a bit more constant and it will make writing playbooks a bit more easier. Now, I shall be creating a new directory for my exercises, MK dear playbooks. And I will enter this directory using the change directory command. Now, I'll create my inventory file. And within my inventory file, I will place server a, server B. And that will also create a group called servers, which will contain both server as well as server B. All that's left now is also to create an Ansible configuration file using VIM. I will start the default section and specify the remote user that ansible we'll be using in order to connect to the manage hosts. And this will be the user automation and also the inventory file, which is present in slash home slash automation slash playbooks slash inventory. Now, I will move on to the privilege escalation section, where I will specify that become equals true. They become method will be set to sudo. And the become user will be set to route. As there is no need for a password, they become as pass option will be set to false and I will just save and exit. Now, I can go on and create my first playbook. It will be named playbook dot YAML. I will start the playbook with the classical three lines. And I will also give a name to my specific play. The name will be create user. Then I will specify two which hosts this playbook applies, and it will apply to all hosts within the inventory. So both server answer for b, and then I will start writing the tasks. My first task be called ensure user is created. And it will use the user module in order to create a user which is named test. And the state of that user will be present. I will save and exit this playbook. And I will first do a syntax check to see if this playbook doesn't have any type of errors or spacing issues. Ansible playbook minus, minus syntax check for my playbook. As you can see, there are no errors. So I think it actually will run on a first try. Then I will run the playbook using the Ansible playbook command specifying the name of the playbook. Let's just wait a bit for Ansible together some facts. And as you can see, both server a, server B have reported a change status. Now, let's use an Ansible ad hoc command for both server and server be using the command module to output the contents of the slash, ETC slash pass VDI file. Judging from the output, we can clearly see the test user does exist with a new ID of 1002. So I will just clear the screen because it seemed my playbook has function correctly. Now, let's edit the playbook to delete the user that we have just created by changing the state of the user from present to absent, save and exit. And let's run it again. We can clearly see that both server and server B have reported that change status, and also by the color, it is yellow. So let's validate our work by running again an Ansible ad hoc command to see if the test user is still present in the past video file. And it seems it is not. So let me just clear the screen and let's document ourselves for additional options for the user module, I'll jump right to the examples at the end of the module. Now, if we look at the first example, we can also specify the UID of the user and also add a comment. So let's do that. I'll just exit the Ansible dog using the Q key and edit my existing playbook to also specify the UID of the user, as well as comment for this particular user. So the UID will be 8 thousand and the comment will be I M test. So now Save and Exit. And let's run this playbook again. Now, if you can clearly see, Ansible has reported that there was no change to neither server a, server B, that is because the state was set to absent and user test does not exist. So there was no need to actually incur a change in a server or server B, I have changed it to present, and now I will run the playbook yet again. So let's wait a bit for Ansible together it's facts. And as we can see clearly from the output, there was a change to both server and server B. So let's run an ad hoc command to see what is in the past VD files of both server and server B, we see the user test with a new idea of 8 thousand n with a comment I M test. So our module and our play worked perfectly. I will just clear the screen and I will edit our existing playbook. Yet again. I will change the name of the task from Ensure user is created to install HTTPD. I will change the module being used from user to yam. Change the name from test to HTTP. Change the state from absent to latest, making sure that I'm installing the latest version of HTTP D. Then I will create a new task, which will start the HTTPD service using these service module, specifying the name of the service HTTPD and the state being started. So let's run it using the Ansible playbook command and see if it works. We'll have to wait a bit for Ansible together it's facts. And as you can clearly see, it has crashed. It failed to install some specific packages, more specifically the HTTP. Now this is because I got the name wrong intentionally. As you can see, it has not moved on to the second task because the first task crashed and we could clearly see the grid color-coding. So I will change the name from HTTP to HTTPD. That is the correct name. So let's try running it again with the correct name. Now, it will take a bit of time for Ansible to both gathering facts as well as installed HTTPD on both server and server B. It seems strawberry has reported a change status and also Server B has reported change status. And the tasks to start HTTPD was done successfully. So I guess it worked. Let's use SSH to connect to server a and do a system CTL status HTTPD, which we can see clearly that it is running. Let's do the same thing also for server B connects through SSH to server B, run a system CTL status, HTTPD, and see if it is running, which it is. So we can clearly see that our playbook ran exactly as planned. Automation is quite awesome. Now, let's sanitize our lab environment by removing the HTTPD packages, which will open our playbook. Deleted last task which starts the HTTPD service and change the state of the yang module from liters to absent. While we are at it, even if it does not impact our playbook. We can also change the name from installed HTTPD to something like remove HTTPD or absent HTTPD, save and exit. And let's run the playbook using Ansible playbook and specifying the name. We'll just wait a bit for Ansible together it's fact. And as you can see, the status for both server a, server B is changed, so that means that the removal was successful. Now let's clear the screen. Let's list the contents of the playbooks directory. And let us remove the Ansible configuration file that we created at the beginning of the demo with the RM command. Let's now use VIM to create a new playbook called playbook to dot YAML. Now, let's start this playbook like any other playbook with three lines, which we'll name the first play by play. And we shall specify additional options, become more be set to true. The remote user will be automation. The become method will be pseudo. They become ask paths will be set to false. And they become user will be set to root. And finally, the managed host will be server B. Now we can start the task section. Now within the test section, I will create a task by the name of create user test. We will use the user module to create a user called test on server B. Now, I will save and exit the playbook and attempt to run it using the Ansible playbook command. Now, I need to specify the inventory file, but a playbook crashed. Why did it crash? Because at become as past is not a valid attribute for a play. So if the options are incorrect, the playbook will just fail on execution, and that is why I deleted the invalid option. Now, I will attempt to execute the playbook again specifying the inventory. And as you can see, it has functioned correctly. So keep in mind that any invalid option within the playbook will cause it to immediately crash. I will just clear the screen now and edit the playbook again. Now, I will add a second play to this particular playbook. I will name this second play. My second play. I will again specify the options become true. Remote user will be set to automation. They become method will be set to pseudo. They become user will be set to route. The targeted host will be both server, a server be through the group servers. Now, I will start my second task section, where I will specify a task with the name of create a second user. On both servers. The second user will be named test to the state of this particular user will be present. Afterwards, I will create a second task with the name delete user test. The module which I will be using will be the user module. Again, I will specify the name of the user which is test, which is keeping mind present only on server B and the state will be absent. Now, I will save and exit my playbook and run it using the Ansible playbook command. Now, let's give Ansible a few seconds to see what it does. So judging from the output, the user test was already present on server B. The second user was created on both servers, DNS server, and the user test was deleted on server be, as it was not present on server a to begin with. So congratulations. You now have a pretty good baseline understanding of what an ansible inventory file is and how to create one. You can create your own Ansible configuration files and nowhere to place them within the Linux file system, you have learned the usefulness of ansible ad hoc commands and how to use them. And finally, you gain a good understanding of how to write a simple Ansible playbook and the benefits that playbooks bring to an symbol. 7. Ansible Variables: Now for our first video, we shall be talking about ansible variables, which we'll discover the utility of variables and where they should be declared in order to access them within playbooks. Lastly, which will have a demo where we should put our learn knowledge into practice. So let's get started. Now, just like in programming languages, variables in Ansible are used to store a value. Variables provides flexibility within playbooks, templates and inventories. And built-in variables can be used to provide system information. Variables can be defined in various places and variable names should only contain letters, numbers, or underscores, or any combination of the beforehand mentioned. Any use of other characters might lead to an error within the playbook. Now as stated previously, variables can be declared in various places. Group variables can be defined in the inventory or the group parts directory inside the working directory. Host variables follow the same pattern. They can also be defined in the inventory or in the host virus directory. You can also declare variables within a playbook that are defined in diverse section of a playbook. Task variables can also be defined within the task. And extra variables can be defined in the command line using D minus E option. So let's look at some practical examples of how variables can be defined within the playbook. Now, at the beginning of a play, we can have the var section where we can define the variable by using the variable name dot, dot, and afterwards the value of that variable, each variable has an associated value. Now, we can also use the variables by using the quotes and accolades as seen on the slide. Variables can also be imported from a variable's file written in YAML format using the vars files section and specifying the path of the variable file. Now, let's move on and see how we can define variables inside the inventory. Now variables can also be declared in the inventory file by specifying the name of the variable and the value of the variable near the host. Or you can specify group variables by creating a new section with the name of the group, dot-dot vars, and then specifying the value of each variable within that section. Inside variable files, which we've talked about previously, they should be defined in YAML format. Now, we can also declare arrays by following the syntax on the slide. Now, for the team variable, we have a member who is Andrew, who has the field of name, and that name is Andrew and also has a new ID of 2001. Then we have Alexander. Now that we learned a lot about declaring and defining variables, let's look a bit at magic variables. Now we have the group's magic variable, which are all hosts and groups within the inventory. The group names, these are all groups. The managed host is part of the host bars. These are variables for the managed host and the inventory host name. That variable is associated with the host name as configured within the inventory. Now, before we finish our section, we shall lastly talk about ansible facts and what ansible facts are and how we can use them. So let's move on. So what are ansible facts? Ansible facts are variables which are automatically discovered when ansible connects to a manage host. They contain information on the managed hosts such as host name, IP address, memory, etc. And they can be used like any other variables. Now, it is useful to know what state the managed host is in as to determine actions that have to be done on that managed host. Ansible facts have a parent child relationship with their elements. So now that we have a baseline understanding of what ansible facts is, let's look at some practical examples on how to use ansible facts in our environment. Now, the first command is, we can see here on the slide is the Ansible server a minus M setup. This will run the setup module and thus print all ansible facts for server a. Now, if I would like to see the FQDN of the managed host, I can use the Ansible underscore facts, FQDN. If I would like to see the default IPV4 address, I can use the Ansible underscore facts, default IPV4 addresses. Now, I can set the gather facts to yes or no, stating if I would like the playbook to gather facts on the managed hosts or not gather facts on the manage hosts. So let's take what we've learned on variables and put that into practice during the demo. See you soon. Now, as you can see, I am in the host variables directory where I have already created the Ansible configuration file and the inventory. As you can see from the configuration file, both the default sexual and the privilege escalation section are in order. Inside the inventory, I have server a, server B, and the group which contains both server as well as server B. So let's start and write a playbook with these three dashes associated. The name of my playbook will be my play, and that will be specifically targeting server a. Now I will start the verse section where I will include my variable. My variable will be called user and we'll have the value of Andrei. So now I can start the task section. My first task will be called create user. I will be using the user module. The name of my user will be the variable user. As you can see, the state will be present. So let me just save and exit this playbook by using WQ. And now let's run the playbook using the Ansible playbook command, specifying the name of my playbook. Antibody is gathering facts. And as we can see from the output, both are green, so there was no change on the manage hosts. That means that my user was already present. So let's change the name of my variable. Now, the value of my variable will no longer be Andrei. The value of my variable will be variable user. And let's run the playbook again using Ansible playbook. As you can see from the output, there was a change on survey. So let's see if both users, Andrei as well as variable user, do exist on the Manage host. So I will run Ansible server a minus m command, and I will read the slash, ETC slash pass VDI file using the cat command. And we can clearly see here that we have both Andre, which has a new ID of 1 thousand, as well as the variable user, which has a new ID of 1004. The playbook has worked adequately. Now let's add another variable to the mix. The variable will be called state and it will have a value of absent. This will destroy our user. So I'll just replace the state from present to the variable of State which I have declared beforehand. I will save annex the playbook and run it again using the Ansible playbook command. Now, the playbook is running and it will take a bit of time for Ansible together or facts. But as we can see from the status of the task, the user has been adequately destroyed. So now let's declare variables inside a variable file. I will create a new directory called Vars. And within that directory, I will create a new file called variables dot YAML. Now, within this file, I will declare my variables. My first variable will be user, which will have the value of test file. And my second variable will be state, which will have the value of present. I will save and exit this file. And I will begin modifying the playbook again. So first, I will delete the variable sections which I already created. I will use the DD hotkeys within VIM, and that will create a new section called vars files, where I will place the path of the variable file which I previously created. So vars slash variables dot YAML. Now I will save and exit my playbook file using WQ. And I will run the playbook file using the Ansible playbook command. Again. Let's give Ansible second together it's facts. And judging by the output, there has been a change to serve array. Let's use an ad hoc command to see what is in the past VDI file again. And as you can see, testfile user does exist and has a new idea of 1004. And our previous user which we created previously, does not exist as we change the state to absent. So let's edit our playbook one more time. I will destroy the virus files section which I created previously. And I will change the state of the user from variable state to present. I will save and exit the playbook. And I will use VIM to open my inventory file. Now on the same line width server a, I will define my user variable. I will write the name of my variable equals the value which will be test inventory. I will save it next the inventory and attempt to run the playbook again. Now, let's give Ansible 1 second together it's facts. And the server a has reported a chase status. Let's use the ad hoc command to CD pass VDI file. And we can see that test inventory was created and has a new idea of 1005. That is because the user variable was imported from the inventory file. Now first I will the user equals test inventory line, and then I will create a new section. This section will be called servers vars. Within this section, I will define my user variable and it will have the value of test inventory group. I will save and exit the inventory. And I will modify the playbook to target not just server a, but the group servers, which includes both survey as well as server B. And I will run the playbook using the Ansible playbook command. Now let's just wait a second. And judging from the status of both server and server B, there was a change and we can see the test inventory group user does exist on both server a as well as on server, be most likely. Now for our next exercise, which will create a directory called host virus, which will hold host variables. I will be using the MKDIR command and then I will change directory within the host var directory. I will create a file called server a. Within this file, I will define a user variable which has the value of test, var server a. I will save and exit this file, and then I'll create a server be file, which will have the value of test var server B. I will save and exit. Then I will use VIM to enter the inventory file and delete this server var sections which we created previously. Now, all that's left is to run the playbook using the Ansible playbook command. Now, let's give Ansible 1 second together it's facts. And judging by the output of the task create user, we can safely assume that the users were created, but let's validate that by reading the past video file. And we can see the test var server, a, server a with a new ID of 1007. Now let's run the same command on server B. Now, judging from the output, we can see the test var server be user was successfully created and has an UID of 1006. So now let's clear the screen of all this clutter and let's modify the playbook one last time, which are entered the playbook using VIM. And I will now define the virus section again. But now I will create an array. The name of the array will be called test array. The first field of the array will be first array. And this will have a field of name with the value of first, and a field called UID with the value of 1011. My second array will be called secondary, and that will also have a field of name with the value of second and a new ID with a value of 1012. Now, let's modify the module, the user module more specifically. And I will replace the user variable with the test array variable dot first array dot name. Now within this module, I will also include the UID field. That UID field who had the value of the variable test array dot first array dot ID. And now I can save it next to the playbook and run the playbook by using the Ansible playbook command. Now, let's just wait 1 second. And judging by the output, there was a change to both survey as well as server B. Let's run an ad hoc command to see what was done. And we can see the user called first does exist. And it does have a new ID of 1011. So it has worked perfectly. Now for the last part of our demo, we shall play a bit with ansible facts. I will use the Ansible setup module to list all the facts associated with diminished host called server. This takes a bit as ansible needs together as fact. And as you can see, we have all the facts listed on our screen. This is not very useful, so I will run the same command now, but pipe the output over to a file called facts dot YAML. And I will use VIM to enter that file. And we can see all the information that as well gathers on manage hosts. Now it is important to take note of the spacing because this tells us which child belongs to which parent, which is essential when working with ansible facts. I will start a new playbook called playbook facts dot YAML. I will start the playbook like any other playbook with three spaces. The name of this playbook will be displayed facts, and it will target specifically server B. Now, I will start the test section where I will have only one task. The name of that task will be show facts. And I will be using the debug module in order to display a certain message. The message will sound something like this. The FQDN is. And then I will use the Ansible fact variable in order to display Server FQDN. So now, after finishing, I will just save and exit and run the playbook using the Ansible playbook command, specifying the name of our playbook, more specifically, playbook facts dot YAML. Now the messages, the FQDN is ansible facts. Fqdn that did not turn out as expected. Keep in mind, I did say that ansible facts or variables because I did not include the accolades. Ansible did not know that was a variable, so he treated it as part of a string. Now, I will modify the playbook at the necessary accolades and then save and exit. And that will run the playbook again using the Ansible playbook command. Now, after Ansible has finished gathering It's tasks, we can see that the message is correct and it shows us the FQDN of server be. So congratulations, It worked perfectly. So congratulations. We learned about ansible variables and how to define and use them within playbooks, we also look at ansible facts and how to use these statuses. Our own playbooks or task. It was quite intensive, so nice going. In the second part, we shall be learning about Ansible loops. So see you soon. 8. Ansible Loops: In the previous video, we talked about ansible variables and also ansible facts. We learn how to use them inside playbooks and also so high versatile and useful they can be. Now we shall look at Ansible loops, what they are, and how to use them within playbooks. So without further ado, let's get started. So what are Ansible loops and why are they useful where loops are used to perform the same task on a set of data without writing it multiple times. Ansible supports loops over datasets and also supports loops over hashes. So to make things a bit more practical, let's look at some sample loops and discuss them. Now the first thing that we have on this slide is a simple loop. Restarts both the HTTPD service and this service. It uses the service module and the name that it calls upon is the variable item. Now the value of item is looped between both HTTPD and crone D. We can also use loops together with variables. We define the variables in the var section. As you can see, the services variable has both the value of HTTPD and crown D. And then we can loop through these services valuable, thus running the tasks to restart both HTTPD as well as grown D. As stated previously, Ansible also supports hash loops. This particular task creates user's part of a specific group and it uses the user module to do so. The name of the user is the item.name variable, and the groups it is part of is the item dot groups variable. These items take different values as you loop through them. In the first iteration, the name will be Andrew and the groups will be automation. In the second iteration, the name will be Alexander and the groups will be automation, thus creating two users, each part of the group Automation. So now that we have a pretty good theoretical overview of loops, Let's go for the demo. In this demo we already have our Ansible configuration file and inventory stuff, as you can see. So let's start and create a playbook called playbook dot YAML. We shall start the playbook, classic three lines and the name of my playbook will be loops. It will target all hosts within the inventory. My first task will be called restart services. And in order to restart services, I will be using the service module. Now, the name of the services which I will be restarting will be the variable item. And the state of the services will be restarted. Now, in order to give values to the item variable, I will loop through both firewall D as well as crown D. I will save and exit the playbook using w q. And I will run the playbook using the Ansible playbook command. Now that antibody has finished gathering, it's fact we can see that on both server, a server be the items firewall D and items grown D, where we started. So I will just clear the screen and I will modify the playbook. Again. I will delete the values through which I am looping. I will start a new section called d bar section, where I will define a new variable. This valuable will be called services. And the services variable will actually have two values. The first value will be crown d, and the second value will be firewall the. And instead of looping through two values, I will be looping through the services variable. I will save and exit the playbook. And I will run the playbook using the Ansible playbook command. And it has crashed. And it has crashed because this is a variable. So I should use quotation marks in order to clearly indicate this to Ansible. I put this service is variable between quotation marks. I will save and exit the playbook again and attempt to run it again with the Ansible playbook command will have to wait a bit for Ansible together it's facts. And as you can see, both on server as well as server be the item variable to the value of crown D and firewall D, the same values that these services value had. Now, I will modify the playbook again. First I will delete the var section which I previously created. And afterwards I will completely delete this service module and the loop, I will change the name of my task from restart services over to create users. And that will be using the user module. In order to do this. Then Emma user will be the variable item dot name because I will be using a hash loop. The UID of my user will be the value of item dot UID. And now I have to loop through an array of values. So the name first will be loop user one, and the UID associated with loop user one will be 1015. And the second value will be loop user to for name. And the UID for loop user two will be 1016. I'll save and exit and run the playbook using the Ansible playbook command. Now we just have to wait a second for Ansible together it's fact. And as you can see, the item.name took the value of loop user one on both service a and service B and loop user two. And the UID took the value of 1015 and also 1016. We can check the results by doing a cat command on the past VDI file of server or server B, and we can see both entities are present. So that concludes our demo. So congratulations you now understand what answerable loops are and how to use them within playbooks in order to make your work less time-consuming and more efficient. In the next part of our course, which we'll be learning about conditionals. So I look forward to seeing you there. 9. Ansible Conditionals: Previously we learned about both variables and loops and their utility within playbooks. In this video, we shall study Ansible conditionals, handlers, and blockers. So we have a lot to cover. So let's get started as opposed supports conditional evaluations before executing a specific task on the target host. If the condition is true, answer, but we'll go ahead and perform the task. If the condition is not true, Ansible will skip this specified task. So let's look at some sample conditionals within Ansible. Now the first example is a simple conditional. Within the bar section we have a variable called service, which is both defined. N has the value of firewall D. The task installs a server is determined by the value of the variable discussed previously. The task also features a symbol conditional, which states that this task is executed only when the variable service is defined. Now the second example is a bit more complicated. We have two variables, condition one, which has the value of one, and condition two, which has the value of 0. We also have a task which will create a user only when condition one has the value of one and when condition two has a value less or equal than one, which is the case. I did mentioned at the start of that video that we shall also learn about Ansible handlers. Handlers are tasks which are executed only if they have been notified by another task. They are written in a separate section of the playbook and are notified by name. Notification only happens when a change is reported by the task charged with notifying the handler. If the task does not report the change, then the handler will not be notified. So let's look at the more practical example. Here we have both the tasks section defined and also the handlers section. First, we shall add a new rule to firewall d, using the firewall d module to permit traffic for the HTTPD service. And this rule will be persistent. Now this will notify the handler called restart firewall D. This handler will restart the firewall, this service using the service module. Lastly, we shall talk a bit about blocks. What our blocks, blocks are clauses which group tasks, and determine how tasks are executed. Blocks in combination with rescue helps with error handling. If the task within the block fails, then the rescue section we'll execute. The always section executes no matter the circumstances. I would like to also mention that blocks can also be used in conjunction with when conditionals. So now that we have a pretty good understanding of handlers, blocks and conditionals, let's go on to the demo. So as you can see, I have already created the Ansible configuration file and the inventory, and that will create the playbook called conditionals dot YAML. I will start this playbook like any other playbook with the three lines. And the name of my first play will be conditionals, and it will target all hosts. Now, I will also declare a variable in diverse section of the playbook called service. This variable will have the value of HTTPD. Now, I can start the test section. Now within the tax section, I will first create a task which is called install a service. And I will use the yang module for this. The name of the installed service will be determined by the service variable value and the state will be latest. I will also include a simple conditional when the service is defined. So that means that the service will only be installed is the service variable is defined. And I will use the Ansible playbook in order to run our conditionals dot YAML playbook. Now, let's wait a bit for Ansible together it's facts. And installing the service will take a bit of time. So don't worry if it takes more than usual. Now, we can see that the change status has appeared on server B. So that means that the HTTPD service was installed on server be most likely. And now the change status has also appeared for server a. I will clear the screen and I will start editing the conditionals dot YAML playbook, which we created previously. First, I will delete the verse section of the playbook and then just delete everything and rename the task which we created previously from installer service to create a new file. I will use the copy module for this. The content which I am placing is a message. And this message states that this is server, a destination where this content will be placed is at slash home slash automation slash conditionals. Now this task will only be executed in a specific situation. Only when the Ansible host name is the same as the value server a. I will save and exit my playbook and I will clear the screen and execute my playbook. So let's wait a bit for Ansible together it's facts. And we can see that server B was skipped, but there is a change status on server a, which will connect using SSH to server a wish list the contents. And now when we read the contents of the conditionals files, it is serve array. So it worked perfectly. So congratulations, we have learned how to use conditionals in a more practical manner. And next we shall be looking at handlers and how to use them. First I will create a playbook called handlers dot YAML. Our start this playbook like any other playbook with three lines to signal the beginning of the playbook. The name of my first play will be handlers, and it will target all hosts within my inventory. Now I can start my test section. Here, I will create a new task, and the task will have the name of add new firewall rule. I will be using the firewall. The module for this service is HTTP, and the state of my rule is present. And I will also make it permanent. That means it will persist after reboot or after the service has been restarted. Now I will notify our handler. The handler will be called restart firewall D. And the keyword here is notified. Then I will create the handlers section. Inside this section, I will create a new handler with the name of re-start firewall D. So it's the same as the one which is being notified. The handler will use the service module and we'll restart the service called firewall D. So the name will be firewall D and the state will be restarted. Now I will save and exit. And let's see if this works as intended. I'll run the playbook using the Ansible playbook command handlers dot YAML. Now, we shall wait for Ansible together. It's facts and as you can see, it has failed. And this was intentional. Now this is because I wrongly wrote the state of the firewall d module. But what I wanted to show you is that if the task has failed or no change status is reported, the handler will not be notified and it will not be executed. So now I will modify the playbook to make it work. I will change the state of the firewall d module from the wrong present To enabled. I will save and exit the playbook. And I will clear the screen and attempt to run the playbook again using the Ansible playbook command. As you can see, antibodies gathering gets fat. The first task was executed without errors and the handler was run. So that means that the firewall, the service was restarted and notified. If we run the playbook again because there is no change status, then the handler was not notified. Thus, the handle was not run. So keep in mind, a handler is only notified if the task charged with notifying it reports a change status. So now let's move on to blocks. First, I will create a playbook called blocker dot YAML. I will start it like any other playbook with three lines. And I will name my first play use of blockers. Now, I will target all hosts and I can start the task section. Now within the tax section, I will first define my block. The name will be installed HTTPD, and then I will include the keyword block. Now the first tasks within my block will attempt to start the HTTPD service. It will be called Start HTTPD, and we'll use the service module. The name of the service is HTTPD and the state is started. Now I can start the rescue section. If something goes wrong in the blog section, the rescue section will automatically start this task. The rescue section will have one task with the name of install HTTPD. It will use the yum module. The name of the service that will be installed is HTTPD and the state is latest. Now before I exit my playbook, I would like to point out that the block and rescue section should have the same level of indentation seems okay now, so I'll just save and exit and attempt to run the playbook using the Ansible playbook command, which will have to wait a bit for Ansible together it's facts Start failed, of course. And as you can see, the installed HTTPD task within the rescue section started. If I attempt to run the playbook again, at this point, the rescue section should not start while they start. Httpd task should start. So let's see if that actually happens and we can see that it is exactly as expected. This concludes our demo. So thank you very much. Congratulations. We have finished this part of our section. And in the next section, which will be deep diving into ansible templates. See you soon. 10. Ansible Templates: We previously learned about loops and conditionals. So let's finish this section by discussing templates. By the end of this lesson, you will have a good understanding of what templates are, how to create them, and their utility in managing files using Ansible. So let's get started. So what makes templates so important? Well, using templates makes managing files easier, as well as customizing those files for the managed host. They are written in ginger to syntax and are deployed using the template module. Templates can both use our ansible facts and variables, and they also support loops and conditionals. Let's make things a bit more practical by first looking at the template module, and afterwards we shall look at some templates sample files. Now this is a simple use of the template module. We have the CRC which states the source where the template is from, the destination, where to place the template file on the Manage host. And we can also set things such as owner, group and permissions for that file on the Manage host. Now these are not the only options that the template module offers and you can use the Ansible document to get more information on it. Now, let's look at a sample template file. The first-line will output the message by FQDN is and the FQDN of the managed host. I can do this by using the ansible facts variable, the second line output variable. This variable has the value of n, the value of my variable. As you can see, this is clearly a variable by the accolades. The third example is meant to show you how a for loop functions within change that to syntax the variable service loop through the values of these surfaces variable. The fourth example is also a loop, but the variable service only loop through the value of the services variable except the value of HTTPD. And the last example shows you how to create an if conditional using ginger to syntax. So now that we understand how templates look and how to deploy them using the template module, let's do something more practical within the demo. See you soon. Now. As you can see, I have already created a configuration file and the inventory. So let's get to creating the playbook. I will name it playbook dot YAML. Now, I will start the playbook with three lines and the name of my first play will be called templates. I will be targeting all hosts within my inventory. And now I will start the test section. Now the name of my first task will be called template placement. And I will be using the template module. First, I will specify the source of the template, which will be in slash home slash automation slash templates slash template. The destination where it will be placed on the managed host. The destination will be slash home slash automation slash templates. I will save and exit the playbook using WQ. Then I will create the template file. So the template file will contain the following content. My host name is, and I will use the ansible facts variable in order to personalize this message. For each manage hosts within the inventory, I will save and exit the template using WQ. And then I will attempt to run the playbook using the Ansible playbook command. So let's just wait a bit for Ansible together it's facts and see the result. Though Ansible has reported the change status on both server and server B. So let's use an Ansible ad hoc command to see the contents of the templates file. We shall first look at server a using the command module to run a cat command on slash, home slash automation slash templates. And as you can see from the message, my host name is server a. Let's run the same command, but now on server B and C, if the host name is server B, which it is, our template file has worked perfectly. Congratulations. I will now just clear the screen and we shall resume the demo. Now, let's edit our template file. I will delete what we wrote previously, and I will replace it with a for loop. So I will use d for host in groups. All this means that the host variable will go through all these servers within my inventory. I will close the accolades and I will write the variable host vars, host, ansible, facts, hostname. And I will end the four Using the end for statement. I will save and exit the playbook, and I will attempt to run the playbook using the Ansible playbook command. Now, let's just wait a second for Ansible together it's facts. And judging from the output, it has reported a change status on both server and server b. So let's see what's in the template files on server be. The message is server a, server B. And the same message is also present on server a. Now that is because within my inventory, I only have server and server be the host variable which loops goes through all hosts within my inventory, which our server and server B. And writes them within the template file. Now, I'll create a new group called Just server a. And I will attempt to change the template file. Again. I will change the groups to just server a new group which I have just created. And now I will save and exit this change and attempt to run the playbook using the Ansible playbook command. Now the message that should be present in that file should now be server a. So let's validate this by running the ad hoc command previously. And we can see that only server a is within that file, both on server as well as on server. Because that is the group which I was targeting within my template file using the groups variable. So let's now delete everything that we wrote previously. And I will now do a conditional statement. I will start my conditional statement with the if keyword and then write my condition. My condition will be the following. If the host name of the managed host is in the group called Just server a, then I will output a specific message. Now, my message will be the following. That server is in the group, just server a. I will end my condition with the end if keyword and I will start a second one. This second condition, we'll look at the host name of the managed host. And if it is not in the group called Just server a, then it will output a different message. The new message will be the following. I am not in the group. And I will also end this if-clause. Now, I will just save and exit the playbook and attempted to run it using the Ansible playbook command. Now we'll wait a bit for asphalt gathering facts. And let's validate our file which we created using the Ansible ad hoc command with the command module in order to output the contents of the templates file. Server is in the group, just serve array. And let's do this for server be, I am not in the group, so it has worked perfectly. Now, I will clear the screen and edit the template. One last time. I will delete everything that we wrote previously and I will write a new message. The message will be the following. I'll create a new user called N, call upon a variable called user. Then I will write a second line containing the following message. This user shell the comment and call upon the value of the variable comment. And lastly, I'll write a third line containing the user is placed on D and call upon on the variable of server. I will save and exit the template file and begin editing the playbook file. So what I will do, I will add a new section which is called Vars. Well, I will declare the variables mentioned previously. Users should have the value of Andrei, comment shall have the value of my comment, and server will have the value of server. See. Now, I will attempt to run the playbook using the Ansible playbook command. Let's wait a bit. And judging from the output, there hasn't been a change to both server and server B. So let's validate our work using the ad hoc command to check the templates file content. So I will create a user called Andre. This usual shall have the comment, my comment that user is placed on server see, but this is present on both salary and server B. So I called upon variables from my playbook, which worked perfectly. Congratulations. Now you know how to use template files, deployed them, create loops using change attitudes syntax, create conditionals using Shadow syntax and call upon variables within templates. Thank you very much. 11. Importing Playbooks And Tasks: Now, for our first lesson, we shall learn about important playbooks. With this knowledge, we can avoid creating huge playbooks and just create smaller, more specific ones, which we can then import within a larger one and use that to achieve our desired outcomes. So without further ado, there's no point in waiting, so let's get started. Now, why is important playbooks important? When writing long playbooks makes them hard to follow and understand. Splitting a large playbook into a series of smaller playbooks means that they can be reused in other projects as well. Now, smaller playbooks, as you can imagine, are easier to manage and understand. So importing a playbook is a static task, which means the important content is processed before the play starts. Importing a playbook cannot be included inside the play, and they are run in order from top to bottom. So let's look at some practical commands that allow us to use the import playbook function. Now as you can see from the slide, in order to import the playbook, we are using the import playbook command for our first example, we are importing to playbooks, the install dot YAML playbook, and they start dot YAML playbook. Now, our second example is meant to show us that the import playbook function can be used in conjunction with conditionals. As an example, this playbook called installed that YAML is important only when the variable service is defined. Our last example is meant to show us that we can mix imports with play. In this particular example, the tasks of my play will run first and afterwards. The tasks imported from my play two will run after. So now that we have a good theoretical overview of how important playbooks works within ansible. Let's do something more practical within the demo. See you soon. As you can see, I have already created the Ansible configuration file and the inventory within the configuration file, I already had the default section setup and the privilege escalation section. And within the inventory, we have service a and service B and a group called servers, and a small group called Just server a, which contains server a. Let's get started. Now first, I will copy the slash, ETC slash HTTPD slash HTTPD file from its original source over to my working directory. Now, I will use VIM in order to edit my local copy of the HTTPD configuration file. What I'm trying to achieve is to get HTTPD to get its content not from the standard slash var slash log directory. But I will create a new custom directory called website from which it will get its content. Now, in order to do this, I will add a few lines in order to relax access to the default document root. And I will replace everything with flash website. So I will also replace the document who wrote with slash websites slash HTML. Now I can save and exit and continue. First, I will create a new playbook called Install dot YAML, which has the purpose of installing the HTTPD service on managed hosts. I will start the playbook with three lines. The standard beginning that for name of my first play will be called installed HTTPD. It will target all hosts within my inventory, and I will start the tax section. The name of my first task will be installed HTTPD. I will be using D Yammer module for this. The name of my service will be HTTPD, of course, and the state will be latest. I will save and exit this playbook and move on to the next one. I will then create a new playbook. Then your playbook, which I will be creating will be called Content dot YAML. Now, I will start this playbook again with the standard three lines. The name of my play will be called new content, and it will target all hosts within the inventory. Now I can start my test section. Now within my task session, I will have a first task called create path. This will create the path form where my web server will get its content and I will use the file module to create this path. The path will be slash website slash HTML, and the state will be directory, as this will be a directory, of course. Now the second task will be called template placement. And I will use the template module in order to place a template in that path. I will specify the source, which will be called template, and the destination will be slash website slash HTML slash index.html. I will save and exit and create yet another new playbook. This playbook would be called HTTPD dot YAML. I will start this playbook like any other playbook. The name of my first play will be HTTPD configure, and it will target all hosts within my inventory. Now, let's start the test section. Now the first task which I will have will be called copy HTTPD configuration file or copy HTTPD cough. And I will be using the copy module to transfer the HTTPD configuration file from my working directory over to my managed hosts in the slash, ETC. Slash HTTP slash com slash HTTPD. Directory. I will then notify a specific handler. The handler will be called restart. And I will start the handlers section. Now within the handler section, I will create the handler which I am notifying. So I will name it restart, and it will use the service module to restart the service named HTTPD. The state will be restarted. I will save and exit using WQ. And then I will create yet another playbook. Now this playbook will be called SELinux dot YAML. The purpose of this playbook will be to set the correct SELinux contexts to my new slash website path. So I will name the first play as a Linux fix. It will target all hosts within my inventory and within the test section, I will have two tasks. Now the, the name of my first task will be set SELinux, and I will use the command module in order to do this. Now the command that I will run on the managed host is the following. Se manage F context minus a for append, minus T for type, specifying the HTTPD says content T type. And the path which I am targeting, in our case, I am targeting d slash website path and all directories. The d slash website path. This is done. I'll create a new task with the name of restore con, using again the command module to run the following command, restore con minus r for recursive on d slash website path. This will relabel all contents of the slash website path to the new SELinux context. I will save and exit. And now I can start my template. Now that my template will contain the following message. Hi, my name is, and then I will use the ansible facts variable to list the host name of the managed host. So for server a, server, a, server B, that would be silver B. And I will save and exit this template file called template. Now everything is done. Let's just create our master playbook. Let's call it. I will use VIM to create a playbook called playbook dot YAML. And I will start this playbook like any other playbook. And now I will import all the playbooks that we created previously. First, I will import the installed playbook because we need to install HTTPD before we can do anything else. So important, playbook install dot YAML. Then I will import the content playbook because I need content within my HTTPD server. So import playbook content dot YAML. Then I will import the playbook called Ixy Linux dot YAML in order to set the correct SELinux context to my path. More specifically slash website. So important playbook, SELinux dot YAML. And lastly, I will import the playbook called HTTPD dot YAML in order to correctly configure my HTTPD service. Now that everything has been theoretically important, I will save and exit and attempt to run the playbook. We have all the fires here present and accounted for. We have the template, we have everything. So let's use the Ansible playbook command to execute the playbook dot gamma, which we created previously. Now, this will take a bit of time. Ansible has successfully gathered it's facts. Now, it is installing the HTTPD service on both server and server B. As you can see now it's running the second playbook and placing the content, creating the path, placing the template, setting the SELinux contexts, restoring the context and coping the HTTPD configure and also notifying the handler. Let's test it with the current command and we can see the message, Hi, my name is salivary and hi, my name is server B. So it worked perfectly. Congratulations. We now know how to split a large playbook into a set of smaller playbooks, which we can then import in a master playbook and make them reusable. So that is quite awesome. So you can import or include tasks in a play from a text file when using the import function, tasks are important within the playbook. When the playbook is parsed, when using the import function, you cannot also use loops. When using the import function in conjunction with a conditional statement, then the conditional statement will apply to all paths which are imported. Now include this a bit different when using the include function, tasks are added to the play when that point is reached while running the play. When using the include function in conjunction with a conditional statement. Then the conditional statement will decide if the tasks are included or not. When using the include function, you cannot notify any handler for money included task file. So now that we have a pretty good theoretical overview of the difference between including an important tasks from a text file. Let's move on and see some practical commands for doing this. Now in order to import tasks within our playbook, we will need to use the Import Task function specifying the path of our tasks file written in YAML format. In our second example, the tasks within the my task dot YAML file, or only executed each individually when the variable service is defined as the conditional states. And if we would like to include tasks, we need to use the include task function. And this will dynamically include tasks while the play is running. So let we understand how to both include an important tasks. We can move on to the demo. So let's get started. Now, as you can see, I have already created the Ansible configuration file and inventory. I will just clear the screen and now we can create our task file. The test file will be called Create dot YAML. And we'll start with the classic three lines. It will have no name, but we'll use the user module in order to create a user which is defined by the variable of username, the state of the user will be, of course, present. So I will save and exit this text file using the w q command. And now I will create a new task file with the name of template dot YAML. It will also start with the classic three lines. The name of my task will be placed template file. It will use the template module. As expected. The source will be defined by D variable template file. Now the destination will be a bit more unique. It will be a file called my file, but the path to that will be defined by d username variable. So slash home, username slash my file. Now, depending on the username, the path will adjust as you might expect. So now let's create my template file. I will call it template, and the message within my template will be the following, placed by Ansible on, and then I will use the ansible facts host name variable to adjust it and customize it to the manage host. Let's also include an exclamation mark just for fun. So I will just save and exit and I will list the contents of my working directory. And we have all files here so we can work on the playbook file. I will start it with the classic three lines. The name of my first play will be created user, end, place, template. Oops, I think I did the mistake, so let me just correct that it will target all hosts within the inventory. And now we can start the test section. Now, within the test section, I will create a task which is called include task, which will use the include task function in order to include the Create dot YAML file. And I will also define some local variables here, more specifically the username variable, which will have the value of user one. Now I'll create a second task which is called place template. Here I will use also the include task function in order to include the template dot YAML task file which we created previously. Specifying again the username variable with the value of user one. And now I will just save and exit. And I will run the playbook using the Ansible playbook command specifying my playbook path. So let's just wait a bit for Ansible together it's facts. As you can see, both tests were included within the play and they have reported change statuses on both server instead of a or B. So I will connect with SSH on cerebral be output the contents of my file using the cat command, cat slash, home slash users slash myfile placed by Ansible on server be user one does exist. So everything worked out just fine. Congratulations. We have now included task files within our playbooks. So congratulations. Now we know how to import playbooks and also include or important task files within our playbooks. In the next video and last video of our section, we shall see how to target specific host using wildcards, host patterns, or listing them. Thank you very much and see you soon. 12. Targeting Hosts: In the previous lessons, we learned how to import playbooks and also how to include or import tasks files within our playbooks. We shall finish Section five of the security automation with Ansible course by learning how to target specific host within our inventory. So let's not wait and get started. So until now we just used one object to the Ansible, which target within the inventory. Now the group oil contains all holes within the inventory, and the group ungroup contains all servers not present within a group. We can better specify who we are targeting through the use of wildcard and lists. Elements within lists are comma separated. Elements can be excluded by using the exclamation point in front of the host pattern that we have defined previously. So let's look at some practical examples before we move on to the demo. Now for our first example, we have the hosts all statement. Now, if we do this, that means we are targeting all hosts within the inventory. If we instead replace all with ungroup, that means we are targeted all host Janet part of a group within the inventory. We can also specify and targets specific IP is like 192168 dot one, dot one. Now the asterisk is a wildcard character. That means it's a place holder for anything. In our fourth example, we are targeting all hosts with an IP ranging from 1 ninth to dot one, dot one dot 0 until 192168 dot one dot 255. Same goes with the fifth examples. We are targeted all hosts with the name starting with cerebellar, followed by any suffix. That we can also target lists of host by using a comma separated list. And we can also exclude a specific host by using the exclamation point in front of the occlusion together with a coma. So now that we have seen some casual and common host patterns, let's put them into practice within the demo. See you soon. Now as you can see, I have created both the inventory file, any configuration file. Within the inventory file we have server, a server be a range of IPs and two groups, just subarray and just server B. So let's use an ad hoc command specifying the all category and tell Ansible police Toll House. And we have all of them there. We have all the IPs as well as server and server B. Let's list all ungrouped hosts. And we can only find the IP is because server a, server b are in their own separate groups. Now, let's use a wildcard character to list all hosts which have an IP starting with 192168 and followed by anything else. And we can see that they have been correctly shown. Now let's apply the same principle to show a server and server be using the wildcard character to show us any server, which starts with server, followed by any suffix. So it worked perfectly as you can see. So now let's create a playbook. The playbook will be called playbook dot YAML. It will start with the classic three lines. The name of my first play will be test host patterns. It will target specific host, but I'll leave that empty at this point and we can start the test section. Now, my first task will be called the bug. And it will use the debug module to show us a specific message. The message will be determined by the ansible facts host name variable. So if the task is executed on server, it will show server ray. If the task is executed on server B, it will show server B. Now, let's go and complete the host pattern. Now for our first example, I will enter the server a group and they just server B group. So targeting both groups, and I will use the Ansible playbook command in order to execute the playbook. Let's wait a bit for Ansible together it's facts and judging by the output, the task was executed on both server a, server B. So it's correct. Let's edit the host pattern a bit. So I will delete what I previously wrote and write the new host pattern. More specifically, our target all holds within the inventory. Aside from all host starting with an IP of 1 ninth to target both server and server B, but nothing with the IP 192, and that worked adequately. Now, let's do this again and erase the host patterns or add another one. Now, I will exclude also serve array from this particular task. Let's see if just server responds. And judging from the output, the pattern was correctly interpreted and just serve our B has responded. So congratulations. We now know how to target specific host with both our ad hoc commands or within playbooks using wildcards as well as list. 13. Ansible Roles: We shall learn what an Ansible role is and why is it useful, which will also find out what are the components of a role and where can they be placed in order to access them. So without further ado, let's find out what our Ansible roles. So what is an Ansible role? Well, let's start with this. Playbooks can become complex when they are needed to configure multiple system with multiple tasks for each system, Ansible lets you organize tasks in the directory structure called a role. In this configuration, playbooks invoked roles instead of task roles allowed to collect templates, static files, and variables along with your tasks in one structured format. Roles allowed to break down a complex playbook into separate smaller chunks than can be coordinated by a central entry point. Now, if main dot YAML exists in a directory, its contents will be automatically added to the playbook that calls the role. This is where we write most of the things in our roles. Lastly, I would like to specify that when we use the roles section two important roles into a play. The roles will run first before any tasks are executed within that play. Now that we have a baseline understanding of what roles are, let us look at the roles directory structure next. First we have the default directory, which contains default variables which can be overridden in the playbook or inventory. Afterwards we have the files directory, which contains files or scripts needed for the role. Next we have the handlers directory, which contains any handlers that you would have in a playbook. The template's directory is where templates will reside, which will generate files on managed hosts. The tasks directory contains tasks files, they can reference any variables. Handlers are templates without specifying the full path as they are part of the role. Aside from the aforementioned, we also have diverse directory where variables for a role can be specified inside files and then can be referenced elsewhere in a role, the metal directory is used for metadata. Usually this is done for dependency management if a role depends on other roles for its execution. Now, let's look a bit at Royal placement and supple by default looks for a directory called roles in the same path where your playbook resides. If Ansible cannot find the roles directory, it will look in the path specified in the Ansible configuration file under the rolls past setting. Roles path can be specified in order separated by a colon. If the roles path is not specified in the configuration file, it will look in the default paths that is either in the home directory of the user under dot ansible Sasha roles, or in the slash usr slash share slash Ansible slash roles path, or in the slash ETC slash Ansible slash roles path. Now in order to create a directory structure which we discussed in the previous lesson, we shall use the Ansible Galaxy init command specifying the role name. Now, as mentioned in the previous lesson, if we use the roles section to include roles within our playbook, then they're all executes before the test section of our playbook does anything. If we would like to do something before that, we can specify those tests in a new section called pretests. If you would like additional tasks to be executed after the test section, we specify this in the post-test section. I would like to point out that we can also notify handlers within each of these sections. Now, if we do not want to use the Role section, we can also import or include the role. Now, as you know from previous lessons, important is a static operation. That means that the role is parsed before the playbook is run. While include is a dynamic operation, that means that the role is parsed when the playbook reaches that specific task. So now that we have a good overview of the commands need to either create, import or user roles. Let's move on to the demo where we shall make things a bit more practical. Now, as you can see, I have already created my Ansible configuration file and inventory. So now I will use the Ansible Galaxy init command to create my roles path. Next, I will use the tree command to show you my roles path and see that all the folders that I mentioned previously are present. We have the default folder, the files, the handlers, the Metta, the task, the templates tests, and the vars directory. So this is a fully functional role skeleton. So let us start editing our role. First, I will edit de Vargas directory where I will include variables for my role. Now, the first variable which I will include will be called service, and we'll have the value of HTTPD. I will also include a second variable called state, which will have the value of present. I will save and exit and now move on to creating a template file. I'll create this temporary file under the path roles slash templates. And I will name this template file content. The content of my template file will be the following. Hello my name is, and then I will call upon the ansible facts variable host name. So it will be hello, my name is server a, server a, and hello, my name is server. Before server B, I will save and exit. Next I will edit my role handlers. So I'll use VIM to open the roles slash handlers slash main dot YAML file. And I will start editing this one to include a specific task. The name of my handler will be. And it will use the service module to start a service who's named depends on the value of the variable called Service defined in my var section, the state will be set to restarted. I will save and exit this one as well. And now I can begin editing the roles slash tasks slash main dot YAML file, where I will place the tasks for my role, the name of my first task will be installed HTTPD. And I will be using the module to install a surface whose name is determined by the value of the variable called Service defined previously. The state is also determined by the value of the variable called state, which we defined in our vars directory. This task will notify a handler called Start HTTPD. The name of my second task is called content, and we'll use the template module. It will take the template from our role, which is called contents, so that is the source and we'll place it in the slash var slash www slash HTML slash index.html path. Now I can begin my playbook. The playbook will be called playbook dot YAML. It will start with three lines. As usual. My play will be called roll HTTPD. Now, it will target all hosts within the inventory. And now I can start the roles section where I will add our created role called rolls. I will save and exit. And I will run the playbook using the Ansible playbook command and see what happens. So first ansible, we'll get there, it's facts. Then as you can see, the role has taken root. It is installing HTTPD. So that might take a bit. It placed the content and it restarted the HTTPD service. If we use the clear command, we can see the output is hello, my name is survey, and hello, my name is server, be on server B. So to sum it up, we created the role skeleton using the Ansible Galaxy init command. We customize it to our needs and we made it run with no playbook. That is awesome. Congratulations. In the next video of our section, which we'll be looking at ways in which we can obtain third-party roles and use them within our own playbooks. See you soon. 14. Ansible Galaxy: In the previous lessons, we learned what Ansible roles are and also how to create our own role and deploy it within a playbook. Now let's see how we can find and use roles created by other third parties. So let's get started. Now, good place to start finding roles is Ansible Galaxy. Ansible Galaxy is a large public repository of Ansible roles. It contains thousands of Ansible roles. Actually, it has a searchable database that helps Ansible users identify roles that they need. Ansible Galaxy includes links to documentation and videos for new Ansible users, enrolled developers. Now we have the language is HTTPS, Ansible Galaxy. And the Ansible Galaxy command line tool can also be used to search, display, and install, as well as remove analyst roles within our system. Personalizing role is done through the use of variables. And usually each Ansible Galaxy role contains a Read Me explaining what role does. Now, let's look at some essential Ansible Galaxy commands. Now the Ansible Galaxy search command will search the Ansible Galaxy repository for a specific term that we provide. The Ansible Galaxy info command specifying a role name will give us detailed information on that role. The Ansible Galaxy install, we'll install that role and we can also specify the path with the minus p option. We can also install a role using a requirements file to a specified path, we d minus R option. We can list all installed roles with the Ansible Galaxy list command. We can remove a role with the Ansible Galaxy remove command specifying the name of the role that we would like to remove. So let's put those commands into practice within the demo. So let's first use the Ansible Galaxy search command to search for a specific term. In our case, we shall be searching for the term HTTPD. And as you can see, we have received a list of roles which are matching our search term. We have the two k lock trellis monitor, which installs and configures monitoring service. In trellis. We have the AACN p dot HTTPD, which installs and configures PHP on our system. So we have multiple roles associated with our search term. Now, let's use the Ansible Galaxy info command to get detailed information on our role. And we shall specify the stack dot HTTPD role. Now from the output, we can see a description of the role if it is active or not, when it was created, which company created it, how many times it was downloaded. Also the GitHub repo, etcetera. So let's use the Ansible Galaxy install command to install this specific role, specifying its name. Now the role is downloading. After download is complete extraction will begin. We received the output that always tag dot HTTPD was installed successfully. Now let's change directory to d slash home slash automation slash dot ansible slash roles directory. And see if our role is present there. And we can see the stack HTTPD role is and all the directories associated with it. And it also contains a readme dot md file that Read Me dot md file will help us understand what the role does and how we can personalize it to suit our own needs. I first clear the screen, and now I will output the contents of the ReadMe file using the cat command. So within the ReadMe file, we have also roll variables where they are held dependencies and also an example playbook on how the rule works. Now, I will use the Ansible Galaxy and list command to list all installed rolls on my system. And we can see the RV stack HTTPD role which we just installed. Now, I will use the Ansible Galaxy delete command to remove the Aldi stack dot HTTPD role which we just installed. This will crash because keep in mind and be very careful. It is Ansible Galaxy remove, not Ansible Galaxy, delete. So let's do the correct command and the role has been successfully removed. So now that we have a good understanding of the command line interface, Let's look at the Ansible Galaxy website. First, I will open my Mozilla Firefox browser and search for Ansible Galaxy on Google. And as you can see, we have found the link. Now on the Ansible Galaxy website, roles are structured by categories. We have system rolls development roles, networking, cloud, database monitoring, packaging, playbook bundled security, etc. We can also use the Search tab to search for specific keywords. I have searched for HTTPD and various roles as well as their associated labels have popped up. As you can see. Now we can just scroll down and see what type of role we actually need from this particular list. We can also see the creators for each individual role. The documentation button will take us to the Ansible Galaxy documentation where we can find almost everything we need to know about Ansible Galaxy. And the community tab will show us all the members of this community, as well as all their creations. Now before we exit the Ansible Galaxy website, Let's just go and see what we can find in a specific category of roles. As an example, let's go for security. And here we can find roles associated with specific security issues. We also can find the CIS security, which is a role which will help us harden our Red Hat Enterprise Linux CentOS, or other operating systems. And we can download it as well as fine, pretty good documentation on this specific role and how it functions. So let's move on to the last step of our demo, where we shall use a third party role within our own infrastructure. Now first we will install a role called Garlin guide dot MySQL using the Ansible Galaxy install command. After the role has been downloaded and successfully installed, we can see the contents of the girlfriend guy dot MySQL folder and it contains all the necessary directories. Now, I will use VIM in order to enter the read me file of the role and get a detailed description on how this role functions. This role installs a MySQL database on my managed hosts with the following passwords as well as names. And the default variables are stored in the default slash main dot YAML file within the role. So let's look a bit at the default variables present in the default slash main dot YAML file. They are all here and also with comments to make it easier to understand what they actually do. So now I will open an existing playbook and modify it to use our downloaded role. So VIM playbook dot YAML. I will erase the role which I included previously. And I will use d Girls Inc guy dot MySQL role. I will save and exit. And I will run the playbook using the Ansible playbook command. Let's wait for the role to run its course. First, ansible, we'll gather facts. Afterwards. It will conduct all the tasks which were defined within the role. Now, at this point in time, it is ensuring that the MySQL packages are installed on both survey as well as cerebral be. It has already defined the MySQL log error, the MySQL sys log tag, the MySQL PID. So now let's just wait and see what happens. We can see each task that the role is performing on the managed host. And by the end, we should have a functioning MySQL database. So let's test this by connecting to one of our managed host server a, or more specifically server be through SSH and then running a system CTL status, MySQL. And it is active and running. Let's do the same thing also for server B. I will just first clear the screen and then use SSH to connect to server B at this point. And again, run a system CTL status for MySQL. And it's working perfectly. Congratulations, we use the third-party role, deploy a MySQL database, and it worked perfectly. So now we know how to use an access and get third party roles. Thank you very much. 15. Managing Users: Now during the first lesson, we will learn how to manage users and groups using Ansible modules, we will learn how to create users with specific configurations such as UID is supplementary groups, etc. And also how to create and manage groups using Ansible modules. So without further ado, let's get started. Now let's take a look at the user module and its options. The name specifies the username, the shell option specifies the users shell. The groups options specifies some parliamentary groups the user is part of. If I use it in conjunction with the append option, it will add supplementary groups to the existing list. The home specifies the home of the user. Uid specifies DID The comment option as a comment that specific user, while the Create home option specifies a per home will be created for that user or not. The state can be present or absent. The group option specifies the user's primary group. The system option specifies if it is a system account or not. While the generate SSH key and the SSH key file says, if you are going to generate an SSH key for that user and how that file will look for managing groups using Ansible, I will be using the group module in order to specify the group's name, I will be using the name option. The state can be present or absent, indicating if the group should be present or absent on the managed host, I can set the group ID by using the GID option and also state if it is a system group or not by using the system auction, adding and removing a key from N to the known host file is done using the known host module. So now that we have an overview, let's go into the demo. As you can see, I have already created the Ansible configuration file and inventory. And the inventory contains both survey as well as server B. So let's create our playbook. I will name it playbook dot YAML, and start the playbook with three dashes. As usual, I will specify the name of my plane, which is create users, and I will specify the host and it will apply to both server and server B. So within the test section, I will create a new task. That name of that task will be user module, and it will use the user module. Now, I will create an account called sysadmin. The state will be present. This account will also be part of an additional group called Andre. And I'm doing this by using the Groups option and the append option. Afterwards, I will set the shell of this new account to slash bin slash bash. I will give it a UID. The UID for the Sys Admin account will be equal to 1049. I will also add a comment and the value of the comment will be my comment. And lastly, I will not create a home for this account, so I'm setting decreased home option to note, I will close the playbook and I will run the playbook using the Ansible playbook command. Now, let's just wait a bit for Ansible together it's facts and CD output of the user module task. So it has reported that change status on both server and server B. Now, I will use an Ansible ad hoc command in order to validate our work. I will output the contents of the slash, ETC slash pass VDI file. We can clearly see that the last account is deceased admin account with a new ID of 1049 and the comment of my comment. So it has worked perfectly. Let's edit our playbook down. First, I will edit the shell option. I will switch from slash bin slash bash to slash sbin slash no login. So it will have no longer terminal access. Afterwards, I will add it the name of my user. I will create a new user called cis user. Then I will change the UID so we don't have a conflict and the new UID will be 1050. I will set the Create home option to yes. So a home will be created for this, this user. And in that home, I will also generate an SSH key using degenerate SSH key option. Lastly, I will specify the path and name of my SSH key file using the SSH key file option, the firewall replaced in slash home slash user. And we'll have the name of my I D. Afterwards, I will save and exit this playbook. First, let's validate the past VDI file. So since user does not exist, and let's run the playbook using the Ansible playbook command. We'll just wait a bit for Ansible together. It's facts. It has reported a change status on both survey and server B. And I will connect to server a. I'll go over to the slash home slash CIS user directory using the cd command. We can clearly see that the director is present here. But first I will switch over to roots so I might have privileges to access it. And we can see within the slash says user directory that we have the keys present, both the public and the private key. If we check the password file, we have this user created with a new ID of 150 and I cannot access its terminal because the shell is set to as been slashed no login. Now, let's edit our playbook one more time. Now, I will delete everything that we wrote previously using D, D, D keys. And I will change the name of my play from create users to create groups. I will change the name of my task from user module over to group module. And I will switch from the user module over to the group module. In order to manage groups, the name of my group will be called my new group. The state will be present, so it will be present on my manage hosts. The GID associated with my new group will be 10,030 and it will not be considered a system group. So I'm setting the system option to know I will save and exit the playbook. I will run the playbook with the Ansible playbook command. Now, let's just wait a bit for Ansible to do it's things. And it has reported a change status on both survey as well as server B. So let's use an Ansible ad hoc command in order to validate our work by outputting the slash, ETC slash group contents. And we can clearly see that my new group was created and has a GID of 10,030. Awesome. So congratulations. Now we know how to manage both groups and users using Ansible. In the next module, we shall be looking at ways in which we can manage services using Ansible. See you soon. 16. Managing Services: Hello and welcome. In this lesson, we shall learn how to manage services using Ansible. This is an essential topic for any system administrator as knowing how to start and stop services is a key topic in any situation, Ansible makes managing services at scale easy and user-friendly. So without further ado, let's get started and look at how we can manage services using Ansible. For managing services using Ansible, we shall be using these service module. Now, let's cover the service module and its options. First we have the name which specifies the service name that we are managing. Afterwards, we have the state which can be started, stopped, or reloaded. The state defines the state of the service and what it will be set to. Enabled defines if the service will start at boot time or not. And it can be set from yes to no. We also have this leap options. How many seconds will it weight before restarting the sleep option goes together with the restarted state. Lastly, we can also specify arguments. In the last example, we restart the ETH one network interface with an overview like this done, let's go into the demo. So as you can see, I have already created the Ansible configuration file and inventory, and I will start the first play book called playbook dot YAML. I will start with three lines and the name of my first play will be Services. It will target all managed host, so both server and server B. Now I can start my test section. My first task will be called Service module, and we'll be using the service module as the name suggests. I will be targeting the HTTPD service. And I will start that service and enable it to start at boot time. I will save and exit the playbook, and I will run the playbook using the Ansible playbook command. Now, let's wait a bit. As ansible needs to gather it's facts. And we can see a change status on both survey as well as server B. I will connect to server and we will use the system CTL status command in order to see that the HTTPD service is both running as well as enabled. Now, I will exit the session and returned to my Ansible host. I will edit the playbook using VIM. I will change enabled from yes to no. And I will change the state from started to stop. And now I will run the playbook again using the Ansible playbook command. Let's just wait a bit. And as we can see from the output, it has reported a change status. Yet again, I will again connect through SSH to server and use the system CTL status command on HTTPD to see that the service is both disabled as well as stopped. So the playbook has worked perfectly. I will just clear the screen and exit this session again. Then I will edit the playbook yet again. First, I will change the state from stopped to restarted. I will change the Enabled option from no to yes. And I will add the sleep option, which will have a cool-down of ten seconds. So it should wait ten seconds until restarting. Let's see if it works. Now antibodies and gathering it's fact and as you can see, it has ignored the steep function. Now, why is that? As we can see from the Ansible doc command, that sleep is not actually supported by system. The myelin acts is running system D, so it will ignore that specific function, but it will work on other Linux distributions. So let's remember that if we have any issues running a specific module or actually using its options, we can check the Ansible dogs. So congratulations, you now know how to start, stop enabled, disabled, and also add the sleep function to services. In the next video, we shall learn how to manage storage using Ansible. So see you soon. 17. Managing Storage: In the previous lessons, we learned how to both manage services as well as users using Ansible. In this lesson, we will learn how to manage storage using Ansible, we will learn how to create logical volumes, how to create partitions, how to create volume groups and physical volumes. So let's get started. Let's first look at the way in which we can create partitions using Ansible, that is using the partied module. I specify the device name, I specify the number, the state, if it should exist or not, and the partition n, which is the size of the new partition which I'm creating. I can create a volume group using the LV GI module, specifying the name of the volume group, specifying which physical volumes each would use within that volume group and the extent size. I can also create logical volumes with the LV O L module specifying the volume group fur mich space will be gathered specifying the name of the logical volume, the size of the logical volume as well. So now that we know how to create partitions, volume groups as well as logical volumes. Let's see how we can place file systems there. We can do this using the file system module. I need to specify the file system type and on which device that file system will be placed. Then I can mount my device specifying the path. So where it will be mounted, the source, what will be mounted? The file system type used. If it will be mounted or not specified using the state option. We can specify mounting options using the OPS option and the DOM status at this point in our example that is set to 0. So now that we have a pretty good overview of what modules are used for storage management using Ansible. Let's go and start the demo. So as you can see, I have already created the Ansible configuration file and inventory, and I have also created the playbook beforehand. Now the name of my first play is called storage, and it's targeting all hosts, so both cerebri as well as server B. Now let's take a look at the test section. Now within the test section we have four tasks. Now the name of my first task is create LV. This will create a logical volume using the LV AOL module. It will take space from the volume group called the name of my logical volume will be L V 02, and the size will be one gigabyte. The name of my second task is file system, which uses the file system module in order to put an X EFS file system on the LV 0 to volume which I created previously. Afterwards, I will create a mount point, and that is also the name of my third task. I am using the file module in order to create a directory called slash mount point. And lastly, the name of my last task is Mount, which uses the mount module. It will mount on slash mount point my LV zeros to logical volume with a file system of the state will be set to present. It will have the default mount options and the DOM status is set to 0. So let's go over it again. I first create a logical volume using space from the volume group called REL. Then I place a file system there. Afterwards, I create a mount point and I mounted persistently using the mountain module. So let's just save and exit this playbook and run it. I will be using the Ansible playbook command in order to execute it. So let's just wait a bit first for Ansible together it's facts. And let's see the output. So it has reported change status on all tasks. Let's SSH over to server a and use the list block device command in order to check our LV CO2. So as you can see from the output, LV Z12 is a logical volume. It clearly does exist and thus have a space of one gigabyte. It takes a space from the volume group called rail. Now, let's also check if our logical volume is mounted persistently. We will do this by checking these slash ETC slash FS tab file. We have the absolute file to the LV 0 to device, which is mounted on slash mount point. It has a file system of SFS. It uses the default mounting options and the dumps status is set to 0. So it worked perfectly. Congratulations. You now know how to manage storage using Ansible. In the next module, we will learn how to manage network configuration using Ansible, using the CLI module. Thank you very much and see you soon. 18. Managing Networks: Welcome. In the past lessons we learned how to manage users, how to manage storage, and also how to manage services using Ansible. Now, we will cover network configuration and how to manage network configuration using Ansible when I'm speaking about network configuration, also include here managing the firewall disservice on Red Hat Enterprise Linux. So without further ado, let's get started now for managing network configuration, Ansible uses the NMC module, which has a lot of options. So let's look at some important ones. The current name allows us to specify the connection name. The name allows us to specify the interface name. The type allows us to specify the type of connection that it is. Ipv4 option allows us to specify the IP used as well as the subnet mask. The gateway for option allows us to specify the gateway using IP for the state can be present or absent. And the DNS for allows us to specify a DNS address using IP version four. The connection can also be enabled or disabled using the auto connect option. Using the host name module, I can specify the host name of my managed host. So now that we know how to manage network configuration, let's look a bit also at managing firewall D configuration. Using the firewall d module, we can specify the zone if the rule is persistent or not using the permanent option, the state of the rule enabled or disabled. And details about that role such as service, source, port and protocol, ritual or network interface. This is an O relation, not an N relation. I would like to emphasize that if I put more of these in the same module, use it will crash. So now that we have a good overview on both managing firewall configuration as well as network connections. Let's go into the demo. So as you can see, I have already created my configuration file and inventory. So let's write the playbook. I will start the playbook with three lines and the name of my play will be network config. It will target all hosts within my inventory. So both serve very end server B. Now I can start the test section and my first task will be called an M CLI module. I will be using the NM clay module, as the name suggests, in order to create a network connection. My network connection will be named Mike cotton. I will then specify the interface. My interface name will be ETH 0 and the type will be Ethernet. Afterwards, I will go on n specify the IP. Ip will be 192. Don't want sensate dot one, dot one with a subnet mask of 24-bit. My Gateway will be 192168.1.1.2. Then I'll move on to specify the DNS using IPV4, which will be 19168 dot one, dot three. And the state of my connection will be present on the managed hosts. Let me just modify the IPV4 because it's IPV4 and the interface name is NEP. And then I will save and exit. I will clear the screen, and now I will run the playbook using the Ansible playbook command. Let's just wait for Ansible together it's facts and it has reported the change status on both server and server B. So let's connect over to server using SSH. I'll switch over to the root account to have privileges. And I'll get information on the connection using D and M CLI command, judging from the output, micron does exist and it is type Ethernets as specified within the playbook. So now let's use the NM click on show command specifying my icon in order to get more detailed information. And judging from the output, it has all the settings which I specified in the playbook, such as DNS, gateway, IP. Now, I will just exit the session on server a and modify my playbook using VIM. And I will change the state from present over two epsilon so that the connection will be destroyed. And I will run the playbook again using the Ansible playbook command. Just wait a bit for Ansible together it's fact. And judging from the output, the connection has been destroyed. So let's move on with firewall configuration using Ansible. As previously that I have already created the configuration file and inventory for ansible. Let's begin creating our playbook called playbook dot YAML. I will start the playbook with Reliance and the name of my first play will be configured firewall D. It will target all hosts within my inventory. So now I can start the test section. Now the name of my task will be firewall d module. It will use the firewall d module as the title suggests. So first, I will specify the zone, which is the public zone, which is also the default zone. The rule will not be permanent, so it will not persist. After a reboot, the state will be enabled and I will specify port 85 slash TCP as the rule suggests, this means that will permit traffic on port 85 over the TCP protocol. I'll run the playbook using the Ansible playbook command hour. Wait a bit for Ansible together it's facts. And then it has reported that change status on both server and server B. I will change the playbook again. I will replace the port option with the service option, and I will write here HTTP. That means I will permit all traffic to the HTTPD service. I'll run the playbook again using the Ansible playbook command. And after that has finalized, I will again edit the playbook. I will replace the service option with this source option and specify an IP. The IP will be 192168 dot one dot one, which means it will permit traffic from that source. I will yet again run the playbook. I'll wait for Ansible to finish its tasks. And now I will connect over to server or server, be using SSH in order to validate our work. I'm switching over to the root account. And I'm doing a firewall semi d minus minus list all command. And we can see that everything which we put in our playbooks is here, the sources, the services, and also port 85 slash TCP. So it worked perfectly. Congratulations. Now know how to create network connections using the NM clay module and also how to manage the firewall D configuration using the firewall, the module. In the next module, we shall be looking at ways in which we can conduct patch management using Ansible. So see you soon. 19. Patch Management: Welcome back. We previously discussed on how to manage network configuration, manage users, managed services, and also how to manage storage using Ansible. Now, we will learn how to do patch management with Ansible. This is a very useful topic as having patch systems and services is one of the main ways to reduce vulnerabilities and the attack surface of threats. So without further ado, let's get started. One of the hardest parts of being a system administrator is patching systems. Come on vulnerability and exposure notifications, also known as CVs or Information Assurance Vulnerability alerts, also known as Yarbus, are quite often and unique patches to fix them and somehow can reduce the time it takes to patch systems by running packaging modules and spell makes deploying patches easy, fast, and management friendly, as well as scalable to large environments. So let's look at some practical examples next. So for both patching as well as installing services, we can use the yang module. We can specify the name of the services that are to be installed and the state in which they should be found, present, absent, or latest. The module also can sustain the installation of groups of services by using D at character. If I want to gather information on what packages are installed and what versions they are installed at. We can use the package packs module and then list that inside a variable, also known as the ansible facts dot packages variable, which will list all installed packages on our systems and their version. Now in order to use Yum to install Apache services, you have needs a repository where it get those patches or surfaces. We can create our own repository using the yum repository module, we can specify the repo name by using the File option. We can specify the description of the repository. We can specify the base URL for where that repository is accessible from. If it is enabled or disabled. If there is a GPG check or no GPG check. If the state of that repository is present or absent. It will save this file under slash, ETC slash sham repos dot d. So now that we have a good overview of how to use the yang module, Let's go ahead and go into the demo. So as you can see, I have already created my Ansible configuration file and inventory. So now let's create a playbook. I will start the playbook with three lines. The name of my first play will be installed, an Update Services. And I will be targeting all hosts within my inventory. So let's start the test section. Within my test session, I will create a task with the name of install an update services. I will be using the yang module for this. And first I will state the name of the services which I would like to have either installed or updated. First will be HTTPD and afterwards, the firewall, the service, the state will be set to latest. That means it will bring both of these services to their latest version. I'll run the playbook using the Ansible playbook command, playbook dot YAML. And I will wait for Ansible to both gathering facts and conduct the task on the manage hosts. This might take a bit of time as it will either install or update those two services. Now, judging from the output, we can see that both servers did not report a change status. So that means that my services, we're already at the latest version. I will first clear the screen and afterwards I will move on and edit the playbook dot YAML file. I will edit the name. I will switch it from installing added services to install groups of services. I will again use the module, but when it comes to name, I will change the name to add container management. Afterwards, I will just save and exit and run the playbook using the Ansible playbook command. So let's see what happens, which are wait a bit for Ansible to gather it's facts and then see the output. Now as you can see, both survey as well as server, we have reported a change status. So the container management tools, which I wanted installed most likely have been successfully installed on both servers within my inventory. So now our edit the playbook again. I will delete everything in that playbook. I'll create a new play which is called gather facts. It will target both server as well as cerebral be. So all hosts within my inventory. And my first task will be named gather installed packages. And I will use the package facts module to get detailed information on all installed packages on the managed hosts. I will set the manager option to auto. And my second task will be called list all, where I will be using the debug module in order to list the contents of the variable ansible facts dot packages, I will save and exit, and I will run the playbook using the Ansible playbook command. So let's look at the output. Here we can see all packages which have been installed on the managed hosts. We can see their version, we can see their name, we can see the distribution, we can see their stores, etc. So this is how we can make an inventory on all installed packages on our managed hosts. I will again delete everything within my playbook. And I will create a new play called configure repo with the following tasks. The name of my first task will be named configure young repo, and we'll use the yum repository module. Now, the name of my file will be my new repo. The name will be my repo, the description will be HelloWorld. The base URL will have a made-up value, so it will be http, my test.com slash URL. The enabled status will be set to know. The GPG XX status will be set to no end, the state will be present. Now I can save and exit and run the playbook using the Ansible playbook command. Now, let's just wait two seconds for the play to be executed. It has reported change status and we will use SSH to connect over to server a. I will be switching the user over two root, so I might have privileges. I will enter the slash ETC slash m dot three posts dot d directory. And here is where we have the new repo dot repo file, which does contain all the options which I previously mentioned. So congratulations. Now you know how to install services, how to patch services, you're using Ansible, how to deploy yum repositories, and also how to gather facts on installed packages, on manage hosts. 20. Important Ansible Modules: Hello and welcome back to the security automation with Ansible course. In the previous lessons, we learned how to use Ansible to do basic system administration tasks. In this lesson, we shall go over the most important Ansible modules which you could need in your quest to implement automation within your organization. We shall discover how to archive files using Ansible and not just that, but also how to write specific lines within text files, how to copy specific text files, and also how to create directories files, etc. We will finish this lesson with a demo in which we will put into practice some of the modules that we shall be discussing. So let's not wait too much and let's get started and let's look at some core Ansible modules. Now first we have the line in file module. Now this module ensures a particular line is in a file or replacing an existing line using a back reference regular expression that we already know how to use using Linux. This is primarily useful. Want to change a single line in a file only. So if you want to change multiple lines, either use a template or create a new file which you can copy on the Manage host. This is especially useful if you're changing one setting from an SSH D configuration file from yes to no or from no to yes. Let's look at some examples on how lining file functions so that we can learn how to use it within our organization. Now the first example will ensure that the default Apache port is 8080. We have the module lighting file, the path of the HTTPD configuration file, which is slash, ETC slash http slash slash http.com. We have the regular expression it is looking for, which is less than. And it will insert the line listen 8080 after it finds the than keyword. Next example ensures that SELinux is set to enforcing mode, again, using the line in file module. First we specify the path with the slash ETC slash SELinux config path than it looks for the line which contains SELinux equals, and we'll change that line to SELinux equals. Enforcing. The last example, we'll make sure that the group wheel is not in the pseudowords file. It is looking in the slash, ETC slash pseudowords configuration file. The state is set to absent, not present, and is looking for the regular expression of a line which starts with percentile. We'll, now that we have a pretty good theoretical overview of how the module lighting fireworks, Let's move on to the next module, which is find, which does a real-time search within the managed host. Now the find module works exactly like the find command within the term null. It doesn't Real Time Search and returns a list of file based on specific criteria, such as name, such as owner, group, owner, missions, date, when last access, et cetera. The find module is extremely versatile and it is extremely useful if we are trying to find something on a managed host and return the path of that specific something that we are searching for. So without further ado, let's look at some practical examples on how to use the find module. Within. The first example, we'll recursively find slash TMP files or lower than two days. We can see that we are using the find module. It is searching within the slash TMP directory. The age is set to two days and the recourse is set to yes, that means it is recursively searching for any file which is older than two days. The second example we'll find slash var slash log files equal or greater than ten megabytes, ending with determination of dot old or dot log dot g z. Again, it uses define module. It is searching within the slash var slash log directory. The pattern it is searching for is anything which ends with slash old and anything which ends with slash log slash G, Z. The size option is set to ten megabytes. That means all files within the slash var slash log bath, which have that name and the size greater or equal to ten megabytes will be returned by the find module in part this particular case. Now, in the last example, we will attempt to find all directories present within slash var slash log, excluding the NGINX and MySQL directories. The file type is set to directory and it excludes, as you can see, NGINX and MySQL. So the find module is extremely versatile. Now let's move forward. Now let's look at the module which we can use in order to schedule regular and repetitive jobs. This is the crown module. We can use this module to manage crontab and environment variable entries. This module allows you to create environment variables and named contract entries, update or delete them. When contact jobs are managed. The module includes one line with the description of the crontab entry and Ansible name corresponding the name pass through the module which is used by future Ansible module calls to find and check the state. When environment variables are managed, no comment line is added, but when the module needs to find slash check the state, it uses the same name parameter to find the environment variable definition line. I would like to point out that when using symbols such as percentile, they must be properly escaped. Now to sum up what I've said previously, antibodies crowd module is used to manage the Chrome tab or manage host. And when it does this, it also adds an entry with hashtag, Ansible, and the Cron job that it has created. So let's look at some practical examples of how this works. The first example ensures a job that runs at 25 exist. It is using the Chrome module. The name of the job is check the ears. It is running at minus 0. And when it comes to the, our option, we have five and then we have also coma two. That means it's running both at our file as well as at our two. Now the job which is running is a long listing. Redirect its results to d slash dev slash null path. We can also use crontab to remove jobs. We can ensure that all job is no longer present. That means it removes any job that is prefixed by the hashtag, Ansible and all job from crontab. We are using the Chrome module. The name is an old job and the state is set to absent. Lastly, we can also create a job which runs a specific script. Again, we are using the Chrome module. The name of the job is a job for reboot. The special time is reboot and the job is running the script present at the slash home slash job dot SH path. So now that we know how to create recurrent job using the Cloud module, let's look at something simpler. More specifically the module. While the Chrome module is used for recurrent or repetitive jobs, they add module is used for onetime jobs. This is extremely useful in situations such as when I want to create a specific user at a specific time, or when I want to send an email at a specific time. So let's look at the ad module. The first example, we schedule a command to execute in 20 minutes as the user root, the command is the listing, as you can see, which then sends its results over to the slash slash null path. Count is 20, and the units used for that count our minutes. So in the second example, we can also use the Add Module to match a command to an existing job and delete that job. We have the command here. And if that command is present within the job queue, then the state will be moved to absent. That means that the job will be destroyed. Within the first example, we can use the Add Module to schedule a command to execute in 20 minutes, making sure it is unique in the job queue. We are using the app module. We have the command, the count, which is 20, the units which are minutes, the option unique which is set to yes. That means if it finds a similar job within the queue, then this job will not be created or done. So now that we know how to both scheduled recurrent jobs using the clone module and onetime jobs using the app module. Let's now look at the file module, which is useful for managing both directories as well as files. Now the purpose of the file module is primarily to set attributes of files, symbolic links or directories. It can also create or remove symbolic links, directories or file. If we want to ensure that a certain path exists, or if we want to make sure that the etc directory is removed, then we will need to use the file module. So even if it is a simple module, it is one of the most useful molecules present in Ansible. I think it could clearly make the top 100. So without further ado, let's look at some examples on how to use the file module. So in the first example, we can use the file module to give insert group permissions to an existing file. We have the path of the pile that we are targeting. The owner is set to route, the group ownership is set to route, and the permissions are set to 1777. That means all entities. So the user owner, the group owner, and the other entities all have read, write, and execute privileges, so not very secure from that end. In the second example, we are using the file module to create a symbolic link. We have the source of that symbolic link and the path is slash files slash to slash link, slash two. And the destination where that link will actually be created. The owner of the link will be set to route. The group ownership will be set to route, and the state will be link, indicating that what we are creating is a symbolic link to our file. The third example, which we'll be using the file module to create a directory if it does not exist. We have the path where that directors should be present. The state is set to directory. And we also have the permissions associated with that directory. So 755, that means that the user owner has read, write, execute privileges, while both the group owner and other entities only have read and execute privileges. So now that we know how to create and manage files using the file module, let's also look at the archives module for managing archives. Now we can use the archive module to create or extend and archive. The source and archive are on the remote host and the archive is not copied to the local host. Source files can be deleted after archival by specifying the option remove equals true. So we can use the archive module to create archives and specify also decompression algorithm which is used for those archives. So let's not wait and let's look at some practical examples of how to use the archive module within Ansible. Now for the first example, I will be using the archive module to compress the directory slash path slash to slash foo into the archive present at slash path slash to slash foo dot t, g, z. As you can see, the two options that I am using are the path to the directory and the destination of my archive. For the second example, I will compress a specific regular file and remove it. I'm moving it by specifying the Remove option and setting that to yes. And in the third example, I'll create a zip archive of a specific file. Again, using the archive module, I'm specifying the compression format through the format option which is set to zip. As you can see. Now that we have a good overview of the archive module and how to create archives using it. Let's also look at the opposite, the unarchive module and how decompress archives within Ansible. The unarchive module unpacks and archive. It will not unpack a compressed file that does not contain an archive, though. By default, it will copy the source file from the local system to the target one before unpacking, we can also set the remote SRC option to yes, to unpack an archive which already exist on the Manage host. So now that we understand what the archive module does and how it functions, Let's do some practical examples of how it should look within a playbook. So for our first example, we shall be going for a simple extraction. We will extract the food dot TGC archive into the slash var slash lib slash foo directory. We have the source, which is the archive, and the destination where that archive will be decompressed. Now for our example, example, we will unarchive a file that is already on the remote machine. Again, using the unarchive module, we have the source which is the slash TMP slash foo dot zip file. It will be decompressed in the destination, which is slash usr slash local slash bin. And the remote source is set to yes, as you can see. Lastly, we can also use the unarchive module to decompress a little file that needs to be downloaded within the source field. I'm not putting a specific folder or directory, but link https.example.com slash example dot zip and the destination where that archive will be decompressed. So that means it will download the archive from that link and then decompress it. Now that we understand and know how to both create archives using Ansible as well as decompressed them. Let's move on to the fetch module and how we can fetch things from the managed hosts. Now the fetch module works like the copy module, which we've used multiple times within the demos. It is used for fetching files from remote machines and storing them locally in a file tree organized by host name. Files that already exist at the destination will be overwritten if they are different than the ones at the source. Now the fetch module is extremely useful for day-to-day system administration tasks. As an example, let's say that I want to centralize all logs from my managed host. That means I will find them and fetch them to my local machine in an organized and structured way. So let's look at some practical examples on how to use the fetch module. Now for our first example, I will first specify the source. So what file MI fetching and the destination where that file will be placed, the path will be slash TMP slash pitched than the host name of the managed host slash TMP and the file which was fetched. Now I can also specify a path directly to the fetch module by using the flat option and setting that to yes. And for our last example, I can also specify a destination path, again using the flat option set to yes. So now that we know how to get files from managed using the fetch module. Let's now look at the URI module. Now for our first example, we can use the URI module to check that you can connect using a GET command to a page and it returns a status of 200. We have the URI module and the URL we are attempting to connect to, in our particular case, the URL http, www.example.com. Now, we can also use the URI module to check the page returns a status of 200 and fails if the word awesome is not in the page contents. We can do this by first specifying the URL of the page we are trying to connect to. Then setting the return content option to yes, registering this content in a variable called this, and then specifying a failed condition, failed when awesome is not in this dot content. And lastly, we can also use the URI module to post from contents of remote files specifying an URL. The method will be set to post the source and the remote source option will be set to. Yes. So now that we have a good overview of the URI module, let's also look at the GET URL Module used for downloading things with Ansible. Now for our first example, I will be downloading the food.com file using the GET URL module, specifying the URL of that file, the destination, where it will be placed on the Manage host, and the permissions associated with the new file. In my particular case, it's 0440. So both the user owner and group owner have read privileges while others entity has no privileges. Now we can also use the GET URL module to download the file and forced basic authentication. Again, specifying the URL and the destination of where that file will be placed. And we can force basic authentication by fitting the first basic auth options to yes. And lastly, we can download the file from a file path using the GET URL module, specifying the URL and the destination. Quite simple, isn't it? So now we know how to both interact with web pages and download files from the online environment using the URI and get URL modules. Let's look at the script module next. So the script module takes the script name followed by a list of space delimited arguments, either a free form command or Cmd parameter is required. We can see this in the examples ahead. The local script at the path will be transferred to the remote node and then executed that given script will be processed through the shell environment on the remote host. So now that we understand how the script module functions, Let's look at some practical examples and how we can use this within our own organization. So for our first example, we shall run a script with arguments free form. We have the path to the script minus, minus some argument and when we specify those arguments. Now for our syndicate example, we can run a script with arguments using the command parameter. We have the script module. The command is set to slash sum slash local slash script dot SH. And then we have the arguments through the minus, minus some argument 1234. And lastly, we can run a script only if the file dot text does not exist on the remote host. We have the link towards the script, and then we have the arguments which details that the script will only run if the file does not exist on the managed host. So if we want to use air sync using Ansible, then we will have to use the synchronized module. Now, desynchronize module is a wrapper around arcing to make common tasks in your playbooks quick and easy. It is run and originates on the local host where Ansible is being run. Of course, we can also use the command module to call N'Sync ourselves. But if we do that, we also have to add a fair number of boilerplate options and host facts for that to work using the synchronized module, This is easier and quicker. So let's look at some practical examples on how to use the synchronized module. Now for our first example, I will be using the synchronized module to synchronize the source on the control machine to the destination on the remote host. This is done by just using the synchronized module and specifying the source and destination paths. Now for our second example, I will synchronize the source and destination with the Earth's think protocol or push by specifying both the source and the destination. And lastly, I will synchronize using the air sink protocol pool. By specifying the mode, the mode will be set to pull the source and the destination paths. Now within answer, well, we also have the Add Host module. The ad host module is used to update the inventory which we are working with. It uses variables to create new hosts and groups in the inventory for use in later place of the same playbook. It takes variables so we can define new hosts more fully. It is extremely useful, especially if we want to update our inventory within our own playbook or within a specific role. So without further ado, let's look at the Add Host module within Ansible, how it works and how it can help us. Now for our first example, I will add a host to the group called just created with a variable associated to that host of foo equals 42. I am using the Add Host module. The name is specified through the variable IP from EC2. The groups it will be allocated to is called just created. And we also have the variable foo with a value of 42 declared. Now we can also use the Add Host module to other host to multiple groups. We specify again the host name and then we can specify all groups that host should be part of. And lastly, we can add a host with a nonstandard port local to your machines. This is done by first specifying the new IP of the host, as well as the port through which Ansible can access that particular host. Now that we understand how to use the Add Host module within ansible, let's look at the ways in which we can also set some custom ansible facts through the set fact module. The set fat module allows us to set variables associated to the current host. These variables will be available to subsequent place during an Ansible playbook run, we had the wholesale credit on by setting the cacheable option two years to save variables across executions using a fact Cache variables will keep the set fact precedents for the current run, but will be used cached precedents for subsequent ones. Now that we understand what the set fact as well module does, Let's look at some practical examples on how we can set custom facts within our playbooks. So for our first example, we shall set some facts that will persist. In fact, cash, we have the fact and the value of that fact, the other factor and the value of that other facts and the cacheable option is set to yes. For the second example, we can also create lists and dictionaries variables. We have one dictionary and the values of that dictionary, we have one list and the values within that list keep in mind we can also make these persistent by setting the cacheable option to yes. Now as you can see, I have already created the Ansible configuration file, as well as the inventory. I have set the default section and also the privilege escalation section. And within the inventory, we have server a, server b, n two groups, just a very ingest server b. So now let's start by looking inside of these playbooks. First, we shall look at the archive playbook. This is where I am using the archive module to create an archive on the managed host. So let's look at this playbook in more detail. The name of my first play is called archive module. It is targeting all hosts within my inventory. Within the test section, I have defined two tasks. The name of my first task is archive. The name of my second task is archive format. Within my first task, the path is slash home slash automation slash archive. That is a folder or directory which exists on the managed host. From that folder, it will create an archive called slash home slash automation slash Archive dot GZ. That is what my first task is doing. Within my second task, I am creating an archive which has the format of zip. You can clearly see this because I have specified the format option and I have said that to zip. So now that you understand what the archive playbook does, I will save it exited using the W key commands and then enter the unarchive dot YAML playbook. Within this playbook, I have only one task and the name of my task is an archive module. I have here the source of my archive and the destination where that archive will be decompressed. As you can see from the host section, this particular playbook is targeting or hosts within my inventory. And I would also like to mention that the name of my play is an archive so that we understand how the unarchive dot YAML playbook works. We'll save and exit, and let's go into a new playbook. Now, the playbook that we are going into now is called schedule dot YAML. Let's look a bit at this playbook. So the name of my play is scheduled and it is targeting all hosts within my inventory. So but server a as well as server be. Within the tasks section. I only have one task. The name of this task is create a scheduled task and is using the clone module. The name of my task will be run my task. The job which is running is eco test. It is running on the fourth month, the fifth day, 17 hour, and every minute of that time. The every minute part is done through the use of the wildcard character Asterix. So now that we understand how this works, I will save and exit this particular playbook, and let's move on to the next one. So I will use WQ, save and exit and enter the onetime job playbook. Let's look a bit at the onetime job dot YAML playbook. The name of my first play is called app module. It is targeting all hosts within my inventory. So both survey as well as server B. Within the last section, I only have one task defined. The name of my tasks is at and uses D at module, the command which is running will be Echo Test, the count will be ten, and the units is set to minutes, and the command has to be unique. This means that I have, I will be scheduling a job which will be running in approximately ten minutes, which will return the result of the eco test command. If a job already does exist with the same command at the same time, then this job will not be created as it has to be unique. So now that we understand how this particular playbook works, Let's just go into the next one, which is called directory dot YAML. So let's look a bit at the directory dot YAML playbook. The name of my first play is called fire module. As you can see, it is targeting all host within my inventory. So both server as well as server be within my test section. I only have one task define, which has the name of file creation. It uses the file module. The path associated with my file module is slash home slash automation slash newly created. The state is set to directed, the owner is set to route, the group is set to automation. The privileges are 0777. That means all entities have read, write, and execute privileges. So upon executing this particular playbook, I should find a directory called newly created within the slash home slash automation path. So now that we understand how this particular playbook functions, I will just save and exited using the w q command inside VIM and enter the next playbook called file dot YAML. Again, within this playbook, I have one play. The play is called file creation, and it's targeting all hosts within my inventory. So both survey as well as server B. Now within the test section, again, I only have one task. The name of my task is file. The module which is being used is file. Now the path associated to this particular file is slash home slash automation slash test file, and the state is set to touch. That means that upon executing this playbook, a file called testfile should be present in these slash home slash automation path. The file should be empty and should have no content. So now that we understand what this playbook is meant to do, Let's move on to the next one, which is called lining file dot YAML. Now let's look a bit at this particular playbook. Now the name of my play is enabled SSH forwarding this targeting all hosts within my inventory. So both subarray as well as Thurber be within the test section. I only have one task defined. The name of that task is change SSH D configuration file or change SSH D config. This uses the line in file module. Now the destination is slash, ETC, slash SSH, SSH D config. This is the configuration file for my SSH service. Backup is set to yes and is looking for a specific regular expression, that means the line starting with x 11 forwarding. This line will be replaced with the line which I have defined in the line section. That means x 11 forward bidding, yes, the state is set to present. So that means that the new line will be present in my SSH D config file. So at the end of executing this playbook, theoretically speaking, my SSH D configuration file should permit x 11 forwarding. I will save and exit. And let's enter the new playbook, which is logs dot YAML, using VIM. So let's look a bit at this particular playbook. The name of my play is called logs, and it's targeting all hosts within the inventory, so both server and server be within my test section. I have two tasks. My first task is called find loads, and this uses the final module. I will be looking in the path called slash var slash log. I'm looking for all files which have the termination dot log recursively. And I will register the result in a variable underlying logs. Now afterwards, I have my second task. Now my second task is called Get logs and uses the fetch module. Now, what does it actually fetching? It is fetching the item dot path variable, that is what the source and the destination is slash home slash automation slash logs. Lastly, I will loop through the values of the underlying logs dot files variable. This variable was defined by our find module through the register command, and that is why the item dot path variable has the path of all logs found using that module. So now that we understand how this playbook works, I will just save and exit this particular playbook. And we can start executing our playbooks. So I would first clear the screen and I will run Ansible playbook. And I will start with the onetime job playbook. We just have to wait a bit for an animal to gather it's facts. And it has reported a chase status on both server and server B. I'll connect through SSH on server and run the app q command. But first I need to switch user to route so we can see the job present. Here. I will clear the screen, exit, exit again. And now I will run again a new playbook using the Ansible playbook command. The second playbook which I am testing is the schedule dot YAML playbook. So let's just wait a bit for Ansible together it's facts. Now let's use SSH to connect over to server or server B and test our work. I will switch user to root. And now I will use the crontab minus e command. And we can clearly see the job has been successfully created and also with the hashtag and suitable name. I will clear the screen. I will exit and close my sessions. And then I will begin running a new playbook using the Ansible playbook command. And I'll run the directory dot YAML playbook. Let's just wait a bit for Ansible together it's facts and it has reported a change status on both server and server B. And we can clearly see the newly created directory with the 077 permissions. I will close the sessions and again, attempt to run the Ansible playbook command to run a new playbook. Now, I will run the file dot YAML playbook. Now let's just wait a bit for Ansible together it's facts, it has reported change status on both server and server B. I will use SSH to connect. And we can see the test file present on server array. And it's clear that it would be present also on server B. Now, again, let's run a new playbook using the Ansible playbook command, the lining file. One more specifically. Now, I already have SSH forwarding present, so no change status was actually present. But the playbook has worked just fine. Now let's look a bit at the archive dot YAML playbook. Okay, so those are the paths that I have to create. I'll go over through server a. I will create the archive directory. I will create the archive format directory. Then I will create some files which I will place within those directories using the touch command. So archive test and then archive format slash test. I will close the session. And now I will do the same thing also for server, be to make sure that I actually have something to archive. So MKDA archive, MK the archive format touch archive test, touch archive format slash test. Now I will close the session from server B, and I will begin running my Ansible playbook using the Ansible playbook command. We'll just have to wait a bit for Ansible together. It's fact it has reported the chase status on server B and a fail status on the archive format task. This is actually a bit of an issue, but this is not due to the wrong written playbook. So let's go over and connect to server a and validate the archive task. And we can see the archive dot GZ was successfully created. So I will just clear the screen. And now let's run our last playbook using the Ansible playbook command. So Ansible playbook logs dot YAML that will get all logs from the managed host and fetch them and place them on the local host. Now, this will take awhile as well. There are a lot of logs to add the actually gathered from the managed host. And these will be placed on the local host in an organized and structured manner. So let's look at the logs, actually ls, and we can see the logs. I will list the contents of the Logs directory. We have four server a server be within this path. We can clearly see that we have all logs that might interest us. I will just use the change directory command to go into the log server or a slash var slash log directory. And we have logs for Anaconda audit, Maria, the air hash, SM, SSS, de-tune D, etc. So everything has worked perfectly. We have successfully centralized blogs from our managed host over to our local host in a easy and structured way. With this demo, we have successfully concluded our course. You now know to use the most popular and useful Ansible modules out there. Congratulations, you've earned it. With this knowledge, you can optimize a lot of system administration tasks within your organization and make everything easier to handle and manage. Ansible has a lot more modules, but that is something that each of you has to research individually depending on the need and context.