Thursday, September 29, 2016

How to setup Jenkins for Continuous Development Integration and build automation on CentOS 7


Introduction
Jenkins is a popular open source tool to perform continuous integration and build automation. The basic functionality of Jenkins is to execute a predefined list of steps, e.g. to compile java source code and build a JAR from the resulting classes. The trigger for this execution can be time or event based. For example, every 20 minutes or after a new commit in a Git repository.
 
Merging code. Coordinating releases. Determining build status. Maintaining updates. If you know the frustration of these processes well enough that the words themselves threaten a headache, you might want to look into Jenkins CI.
Maintaining any project, especially one developed by several team members concurrently and one that might incorporate many functions, components, languages, and environments, is a struggle at the best of times — and at the worst requires a superhuman feat to stay afloat.
Jenkins is here to help. Fundamentally a solution for continuous integration — i.e. the practice of merging all code continually into one central build — Jenkins acts as a headquarters for the operations of your project. It can monitor, regulate, compare, merge, and maintain your project in all its facets.
At its core, Jenkins does two things: automated integration and external build monitoring. This means that it can greatly simplify the process of keeping your code maintainable and keep a close and untiring eye on the quality of your builds, ensuring you don’t end up with nasty surprises when a few of your developers merge their code before it’s ready.

Prerequisites
To follow this tutorial, you will need the following:
·         CentOS 7 Droplet
·         A non-root user with sudo privileges

All the commands in this tutorial should be run as a non-root user. If root access is required for the command, it will be preceded by sudo.

Step 1 — Installing Jenkins
There are two basic ways to install Jenkins on CentOS: through a repository, or repo, and via the WAR file. Installing from a repo is the preferred method, and it's what we'll outline first.
You'll need Java to run Jenkins (either method), so if your server doesn't yet have Java, install it with:
# sudo yum -y install java

In general, if you need a service or tool but you're not sure what package provides it, you can always check by running:
# yum whatprovides service

Where service is the name of the service or tool you require.
Installing from the Repo
Now, run the following to download Jenkins from the RedHat repo:
# sudo wget -O /etc/yum.repos.d/jenkins.repo http://pkg.jenkins-ci.org/redhat/jenkins.repo
The wget tool downloads files into the filename specified after the "O" flag (that's a capital 'O', not a zero).

Then, import the verification key using the package manager RPM:
# sudo rpm --import https://jenkins-ci.org/redhat/jenkins-ci.org.key

Finally, install Jenkins by running:
# sudo yum install jenkins

That's it! You should now be able to start Jenkins as a service:
# sudo systemctl start jenkins.service

Once the service has started, you can check its status:
# sudo systemctl status jenkins.service

This will give you a fairly lengthy readout with a lot of information on how the process started up and what it's doing, but if everything went well, you should see two lines similar to the following:
Loaded: loaded (/etc/systemd/system/jenkins.service; disabled)
Active: active (running) since Tue 2015-12-29 00:00:16 EST; 17s ago
This means that the Jenkins services completed its startup and is running. You can confirm this by visiting the web interface as before, at http://ip-of-your-machine:8080.

Step 2 — Creating Users
Once Jenkins is running smoothly, establishing good security is the next step. From here on out, your exact actions will largely depend on your purposes for Jenkins. However, the following are general guidelines of how Jenkins can best be set up and used, along with some examples to pave the way.
Jenkins provides settings for security and role management, useful for controlling access and defining user actions. We’ll visit that briefly to introduce those concepts. To get to those settings, return to the Jenkins interface via your browser once your service is running (http://ip-of-your-machine:8080). You will see a menu on the left – choose Manage Jenkins from within that. This will take you to a page containing a number of options for customization. You may also notice an an alert at the top: Unsecured Jenkins allows anyone on the network to launch processes on your behalf. Consider at least enabling authentication to discourage misuse. This is Jenkins’ directive to get you to introduce some element of security to your system.















 







The first step to take here is to go to Configure Global Security, near top of the list of links on the manage Jenkins page. Check the option box for Enable security to bring up a group of options for this purpose. There are any number of ways to configure security on Jenkins – you can read the in-depth explanation in the Standard Security Setup section of the Use Jenkins documentation.
The most straightforward of these options, and the one we will lay out today, has Jenkins use its own database to store user configurations. Under the Access Control section that appeared when we flagged the checkbox, select Jenkins' own user database. Briefly, the other options are to link Jenkins to existing Unix users and groups, to use an organization-wide login (LDAP option), or to allow a Java servlet to manage access. Other options can be added through plugins (we’ll discuss plugins in a bit).
Whether you should allow new users to sign up largely depends on your own needs. In general, however, it pays to restrict access, and allowing users to sign up as they wish can allow a level of openness that can potentially be dangerous. To restrict this, deselect the checkbox marked Allow users to sign up. Once this setting has been turned off, only administrators can create new accounts. In a moment, you'll supply administrative privileges for a user you'll create, and we'll go into detail on adding new users, as well.
Under Authorization, select the Matrix-based security option. This allows some fine-tuning of the controls without resorting to complex setups. You'll see a user named Anonymous is already present. An anonymous user is anybody from anywhere, even when they're not logged in, which is why by default the anonymous user has no abilities. Since this is the initial setup of the Jenkins instance, you must give this user full permissions: there are no users other than anonymous right now, and you're not logged in, so turning off anonymous permissions would effectively cut you off from accessing Jenkins at all.
Use the small button to the right of the Anonymous row to select all permissions. Next, use the User/group to add input field to specify a new user for which to add permissions. Note that this does not actually create a user, but rather specifies permissions for the user you will create shortly.
Normally, you would create a new user first and then specify permissions for them in this part of the form. Since no user exists yet, you'll set up permissions and then create the user.
Enter a username and press Add. Due to a known bug, it is recommended that you keep the usernames lowercase. Give the new user all permissions the same way you did for the anonymous user. This essentially sets up a new administrator.
When you're done, press Apply and then Save.
You will be taken automatically to a signup page, from which you can create a new account. The username of the account you create should correspond to the one for which you specified permissions earlier:




When you finish, you should find yourself automatically logged in.
Return to the security page (Manage Jenkins -> Configure Global Security) and scroll down to the security matrix. Now that you've created an administrative user, you can restrict the permissions for the anonymous user. Deselect all the permissions in the anonymous row, and then click Apply and Save. Your new user will now be the only user with access to Jenkins.
If you turned off the automatic sign up earlier, you might need to manually create additional new users. Here's how:
Return to the Manage Jenkins page, scroll down to near the bottom and click on Manage Users. On the left you'll see a sidebar with links; click on Create User. Enter the information for the new user the same way as you created the first user, and click Sign up. You'll be redirected to the list of users, which will now include the new user. This user will have no permissions, so you will need to repeat the permissions process, going to Configure Global Security, using the User/group to add field to add a row to the matrix, specifying permissions, and clicking Apply and Save. For simplicity's sake, if you have multiple users to create, create them all before moving on to adding permissions.
When creating new users, keep in mind that restrictiveness can be a major security asset. You can learn more about the specific ins and outs of matrix-based security in the Matrix-based Security section of the Use Jenkins documentation.
Typically, the next step is to assign roles to your users, controlling their exact abilities. We won’t go into details in this article, but this is a good article on the subject. Be sure to save your changes after you assign roles.

Step 3 — Installing Plugins
Once Jenkins is installed, minimally configured, and reasonably secured, it's time to make it fit your needs. As found when it is first installed, Jenkins has relatively few abilities. In fact, Jenkins typifies a credo of many software developers: do one thing, and do it well. Jenkins "does one thing" by acting as a middleman for your software projects and “does it well” by providing plugins.
Plugins are add-ons that allow Jenkins to interact with a variety of outside software or otherwise extend its innate abilities. As with many areas of the Jenkins setup, the exact plugins you install will be significantly dependent on your projects.
From the main left hand side menu in Jenkins, click Manage Jenkins -> Manage Plugins. The page you land on shows plugins that are already installed but need updating – you can perform this easily by selecting the plugins you want to update and clicking the button at the bottom.

If you click on Available from this page, you will be taken to a colossal list of available plugins. Obviously, you don't want to install all possible plugins, so the next question is how to select those you will need.
As mentioned, your choice in this matter will depend on your needs and goals. Fortunately, the Jenkins wiki provides a nice rundown of plugins by topic.
This list is definitely worth perusing, but no matter your project, there are a few plugins which you almost certainly should include. Here are a few — some generic, some specific:

Source control
Git, SVN, and Team Foundation Server are some of the more common source control systems. All three of these have plugins in the Jenkins list, and others exist for less common systems as well. If you don't know what source control is, you should really learn about it and start incorporating it in your projects. Be sure to install the plugin for your source control system, so Jenkins can run builds through it and control tests.

Copy Artifact
This plugin allows you to copy components between projects, easing the pain of setting up similar projects if you lack a true dependency manager.

Throttle Concurrent Builds
If you have multiple builds running which might introduce a conflict (due to shared resources, etc), this will easily allow you to alleviate this concern.

Dependency Graph Viewer
A nifty plugin providing a graphic representation of your project dependencies.

Jenkins Disk Usage
Jenkins may be fairly lightweight, but the same can't always be said for the projects with which it integrates. This plugin lets you identify how much of your computing resources any of your jobs are consuming.

Build tools
If your project is large, you probably use a build manager, such as Maven or Ant. Jenkins provides plugins for many of these, both to link in their basic functionality and to add control for individual build steps, projection configuration, and many other aspects of your builds.
Reporting
While Jenkins provides its own reports, you can extend this functionality to many reporting tools.

Additional Authentication
If the default Jenkins abilities for security don't suite you, there are plenty of plugins to extend this – from Google logins, to active directory, to simple modifications of the existing security.

In general, if your project requires a certain tool, search the plugin list page on the wiki for the name of it or for a keyword regarding its function – chances are such a plugin exists, and this is an efficient way to find it.
Once you have selected those plugins you want to install on the Available tab, click the button marked Download now and install after restart.
Now that Jenkins is up and running the way you want it, you can start using it to power your project integration. Jenkins' capabilities are nearly endless within its domain, but the following example should serve to demonstrate both the extent of what Jenkins can do and the beginnings of how to get a Jenkins job started.

Step 4 — Creating a Simple Project
There are a lot of interesting uses you can get out of Jenkins, and even playing around with the settings can be informative. To get started, though, it helps to understand how to set up a basic task. Follow the example in this section to learn how to establish and run a straightforward job.
From the Jenkins interface home, select New Item. Enter a name and select Freestyle project.



This next page is where you specify the job configuration. As you'll quickly observe, there
are a number of settings available when you create a new project. Generally, one of the more important controls is to connect to a source repo. For purposes of this introductory example, we'll skip that step.
On this configuration page you also have the option to add build steps to perform extra actions like running scripts.




This will provide you with a text box in which you can add whatever commands you need. Use this to run various tasks like server maintenance, version control, reading system settings, etc.
We'll use this section to run a script. Again, for demonstration purposes, we'll keep it extremely simple.



If you want, you can add subsequent build steps as well. Keep in mind that if any segment or individual script fails, the entire build will fail.
You can also select post-build actions to run, such as emailing the results to yourself.
Save the project, and you'll be taken to its project overview page. Here you can see information about the project, including its built history, though there won’t be any of that at the moment since this is a brand-new project.





Click Build Now on the left-hand side to start the build. You will momentarily see the build history change to indicate it is working. When done, the status icon will change again to show you the results in a concise form.
To see more information, click on that build in the build history area, whereupon you’ll be taken to a page with an overview of the build information:





The Console Output link on this page is especially useful for examining the results of the job in detail — it provides information about the actions taken during the build and displays all the console output. Especially after a failed build, this can be a useful place to look.
If you go back to Jenkins home, you'll see an overview of all projects and their information, including status (in this case there's only the one):





Status is indicated two ways, by a weather icon (on the home page dashboard, seen above) and by a colored ball (on the individual project page, seen below). The weather icon is particularly helpful as it shows you a record of multiple builds in one image.
In the image above, you see clouds, indicating that some recent builds succeeded and some failed. If all of them had succeeded, you'd see an image of a sun. If all builds had recently failed, there would be a poor weather icon.
These statuses have corresponding tooltips with explanations on hover and, coupled with the other information in the chart, cover most of what you need in an overview.
You can also rebuild the project from here by clicking (Build Now).

Of course, implementing a full-scale project setup will involve a few more steps and some fine-tuning, but it’s clear that without much effort, you can set up some very useful, very pragmatic monitors and controls for your projects. Explore Jenkins, and you’ll quickly find it to be an invaluable tool.

Conclusion
It's highly worthwhile to seek out other tutorials, articles, and videos — there are plenty out there, and the wealth of information makes setting up project integration with Jenkins practically a breeze. The tutorials hosted by the Jenkins team are worth a look.
In particular, bridging the gap between basics and fully fledged projects is a great way to improve your Jenkins skills. Try following these examples as a way to ease that transition.
Additionally, many templates exist for common types of projects, such as PHP applications and Drupal, so chances are strong you won’t even need to set up everything from scratch. So go out there, learn all you dare about Jenkins, and make your life that much easier!

How to Install Git over HTTP on CentOS x








There is already a bunch of posts about setting up Git over HTTP(S), but this one is specificaly targeted at setting it up under CentOS as cleanly as possible. There was bunch of errors that I saw along the way, so I will try to explain the process step by step.

First, you have to install Apache and Git.:
# yum -y install httpd git
# /etc/init.d/httpd start

Now, let’s create directories for git and create our first repo:
# mkdir /var/www/html/gitrepos
# cd /var/www/html/gitrepos
# mkdir repo01 && cd repo01
# git --bare init
# git update-server-info
# cd /var/www/html
# chown -R apache: gitrepos

We are using ‘git –bare’, so that online repository doesn’t have files but only git metadata. That will enable users to push directly to online repository, otherwise they wouldn’t be able to push thier changes. This was the first error I did, I created repo with ‘git init’ and was not able to push later. After the repo is set up and chowned, lets set up apache.

This is my configuration for vhost:
#
# vhost for git repositories (http)
#
<VirtualHost *:80>
    ServerName     git
    DocumentRoot    /var/www/html/gitrepos

    <Location />
        DAV on

        # general auth settings
        AuthName "Git login:"
        AuthType Basic

        # file authentication
        AuthUserFile  /var/www/html/.htpasswd
        AuthGroupFile /var/www/html/.htgroup

        <LimitExcept PROPFIND>
            Require valid-user
        </LimitExcept>
    </Location>

    <Location /repo01>
        <LimitExcept PROPFIND>
            Require group adminlinux
        </LimitExcept>
    </Location>

    LogLevel warn
    ErrorLog  /var/log/httpd/git_error.log
    CustomLog /var/log/httpd/git_access.log combined
</VirtualHost>
#
We can fill up htpasswd file with – htpasswd command
# htpasswd -c /var/www/html/.htpasswd user1
# htpasswd -c /var/www/html/.htpasswd user2
# htpasswd -c /var/www/html/.htpasswd user3

And htgroup with:
# echo "adminlinux: user1 user2" >> /var/www/html/.htgroup

Now, on the client side, do a:

After the first change/commit you do, be careful when you push those changes for the first time.
This is the command I used for the first push:
% git push --set-upstream origin master

And that’s it!...

Friday, September 23, 2016

How To Install Puppet 4 in a Master-Agent Setup on CentOS 7


Introduction

Puppet, from Puppet Labs, is a configuration management tool that helps system administrators automate the provisioning, configuration, and management of a server infrastructure. Planning ahead and using config management tools like Puppet can cut down on time spent repeating basic tasks, and help ensure that your configurations are consistent and accurate across your infrastructure. Once you get the hang of managing your servers with Puppet and other automation tools, you will have more free time that can be used to improve other aspects of your setup.

Puppet comes in two varieties, Puppet Enterprise and open source Puppet. It runs on most Linux distributions, various UNIX platforms, and Windows.

In this tutorial, we will cover how to install open source Puppet 4 in an agent/master setup on CentOS 7. In this setup, the Puppet master server—which runs the Puppet Server software—can be used to control all your other servers, or Puppet agent nodes. Note that we'll be using the Puppet Server package, instead of Passenger or any other runtime environment.

Prerequisites

To follow this tutorial, you must have root or superuser access to all of the servers that you want to use Puppet with. You will also be required to create a new CentOS 7 server to act as the Puppet master server. If you do not have an existing server infrastructure, feel free to recreate the example infrastructure (described below) by following the prerequisite DNS setup tutorial.

Before we get started with installing Puppet, ensure that you have the following prerequisites:

Private Network DNS: Forward and reverse DNS must be configured, and each server must have a unique hostname. Here is a tutorial to configure your own private network DNS server. If you do not have DNS configured, you must use your hosts file for name resolution. We will assume that you will use your private network for communication within your infrastructure.

Firewall Open Ports: The Puppet master must be reachable on port 8140. If your firewall is too restrictive, check out this FirewallD Tutorial for instructions on how to allow incoming requests on port 8140.

Example Infrastructure

We will use the following infrastructure to demonstrate how to set up Puppet:
Hostname
Role
Private FQDN
host1
Generic CentOS 7 server
host1.nyc3.example.com
host2
Generic CentOS 7 server
host2.nyc3.example.com
ns1
Primary nameserver
ns1.nyc3.example.com
ns2
Secondary nameserver
ns2.nyc3.example.com

The puppet agent will be installed on all of these hosts. These hosts will be referenced by their private network interfaces, which are mapped to the ".nyc3.example.com" subdomain in DNS. This is the same infrastructure that is described in the prerequisite tutorial: How To Configure BIND as a Private Network DNS Server on CentOS 7.
Once you have all of the prerequisites, let's move on to creating the Puppet master server!

Create Puppet Master Server

Create a new CentOS 7 x64 server, using "puppet" as its hostname. The hardware requirements depend on how many agent nodes you want to manage; two CPU cores and 1 GB of memory is the minimum requirement to manage a handful of nodes, but you'll need more resources if your server infrastructure is larger. Puppet Server is configured to use 2 GB of RAM by default.

Hostname
Role
Private FQDN
puppet
Puppet master
puppet.nyc3.example.com

If you just set up your DNS and are unsure how to include new hosts, refer to the Maintaining DNS Records section of the DNS tutorial. Essentially, you need to add an "A" and "PTR" record, and allow the new host to perform recursive queries. Also, ensure that you configure your search domain so your servers can use short hostnames to look up each other.

Note: This tutorial assumes that your Puppet master's hostname is "puppet". If you use a different name, you will need to make a few deviations from this tutorial. Specifically, you must specify your Puppet master's hostname in your Puppet agent nodes' configuration files, and you must regenerate your Puppet master's SSL certificate before signing any agent certificates. Otherwise, you will receive this error: Error: Could not request certificate: The certificate retrieved from the master does not match the agent's private key..
Configuring this setting is not covered in this tutorial.

Install NTP

Because it acts as a certificate authority for agent nodes, the Puppet master server must maintain accurate system time to avoid potential problems when it issues agent certificates--certificates can appear to be expired if there are time discrepancies. We will use Network Time Protocol (NTP) for this purpose.

First, take a look at the available timezones with this command:
timedatectl list-timezones

This will give you a list of the timezones available for your server. When you find the region/timezone setting that is correct for your server, set it with this command (substitute your preferred region and timezone):
sudo timedatectl set-timezone America/New_York

Install NTP via yum with this command:
sudo yum -y install ntp

Do a one-time time synchronization using the ntpdate command:
sudo ntpdate pool.ntp.org

It is common practice to update the NTP configuration to use "pools zones" that are geographically closer to your NTP server. In a web browser, go to the NTP Pool Project and look up a pool zone that is geographically close the datacenter that you are using. We will use the United States pool (http://www.pool.ntp.org/zone/us) in our example, because our servers are located in a New York datacenter.
Open ntp.conf for editing:

sudo vi /etc/ntp.conf

Add the time servers from the NTP Pool Project page to the top of the file (replace these with the servers of your choice):

/etc/ntp.conf excerpt
server 0.us.pool.ntp.org
server 1.us.pool.ntp.org
server 2.us.pool.ntp.org
server 3.us.pool.ntp.org
Save and exit.

Start NTP to add the new time servers:
sudo systemctl restart ntpd

Lastly, enable the NTP daemon:
sudo systemctl enable ntpd

Now that our server is keeping accurate time, let's install the Puppet Server software.

Install Puppet Server

Puppet Server is the software that runs on the Puppet master server. It is the component that will push configurations to your other servers, which will be running the Puppet agent software.

Enable the official Puppet Labs collection repository with this command:

sudo rpm -ivh https://yum.puppetlabs.com/puppetlabs-release-pc1-el-7.noarch.rpm

Install the puppetserver package:

sudo yum -y install puppetserver

Puppet Server is now installed on your master server, but it is not running yet.

Configure Memory Allocation (optional)

By default, Puppet Server is configured to use 2 GB of RAM. You should customize this setting based on how much free memory your master server has, and how many agent nodes it will manage.

First, open /etc/sysconfig/puppetserver in your favorite text editor. We'll use vi:

sudo vi /etc/sysconfig/puppetserver

Then find the JAVA_ARGS line, and use the -Xms and -Xmx parameters to set the memory allocation. For example, if you want to use 3 GB of memory, the line should look like this:

JAVA_ARGS="-Xms3g -Xmx3g"
Save and exit when you're done.

Start Puppet Server

Now we're ready to start Puppet Server with this command:

sudo systemctl start puppetserver

Next, enable Puppet Server so that it starts when your master server boots:

sudo systemctl enable puppetserver

Puppet Server is running, but it isn't managing any agent nodes yet. Let's learn how to install and add Puppet agents!


Install Puppet Agent

The Puppet agent software must be installed on any server that the Puppet master will manage. In most cases, this will include every server in your infrastructure. As mentioned in the introduction, the Puppet agent can run on all major Linux distributions, some UNIX platforms, and Windows. Because the installation varies on each OS slightly, we will only cover the installation on CentOS 7 servers. Instructions on installing the Puppet agent on Ubuntu 14.04 servers can be found here.

Perform these steps on all of your agent servers.
Enable the official Puppet Labs collection repository with this command:
sudo rpm -ivh https://yum.puppetlabs.com/puppetlabs-release-pc1-el-7.noarch.rpm

Install the puppet-agent package:

sudo yum -y install puppet-agent

Now that the Puppet agent is installed, start it with this command:

sudo /opt/puppetlabs/bin/puppet resource service puppet ensure=running enable=true

The first time you run the Puppet agent, it generates an SSL certificate and sends a signing request to the Puppet master. After the Puppet master signs the agent's certificate, it will be able to communicate with and control the agent node.

Remember to repeat this section for all of your Puppet agent nodes.

Note: If this is your first Puppet agent, it is recommended that you attempt to sign the certificate on the Puppet master, which is covered in the next step, before adding your other agents. Once you have verified that everything works properly, then you can go back and add the remaining agent nodes with confidence.

Sign Certificates on Puppet Master

The first time Puppet runs on an agent node, it will send a certificate signing request to the Puppet master. Before Puppet Server will be able to communicate with and control the agent node, it must sign that particular agent node's certificate. We will describe how to sign and check for signing requests.

List Current Certificate Requests

On the Puppet master, run the following command to list all unsigned certificate requests:
sudo /opt/puppetlabs/bin/puppet cert list

If you just set up your first agent node, you will see one request. It will look something like the following, with the agent node's hostname:

Output:
  "host1.nyc3.example.com" (SHA256) 15:90:C2:FB:ED:69:A4:F7:B1:87:0B:BF:F7:DD:B5:1C:33:F7:76:67:F3:F6:23:AE:07:4B:F6:E3:CC:04:11:4C

Note that there is no + in front of it. This indicates that it has not been signed yet.

Sign A Request

To sign a certificate request, use the puppet cert sign command, with the hostname of the certificate you want to sign. For example, to sign host1.nyc3.example.com's certificate, you would use the following command:

sudo /opt/puppetlabs/bin/puppet cert sign host1.nyc3.example.com

You will see the following output, which indicates that the certificate request has been signed:

Output:
Notice: Signed certificate request for host1.nyc3.example.com
Notice: Removing file Puppet::SSL::CertificateRequest host1.nyc3.example.com at '/etc/puppetlabs/puppet/ssl/ca/requests/host1.nyc3.example.com.pem'

The Puppet master can now communicate and control the node that the signed certificate belongs to.

If you want to sign all of the current requests, use the --all option, like so:
sudo /opt/puppetlabs/bin/puppet cert sign --all

Revoke Certificates

You may want to remove a host from Puppet, or rebuild a host then add it back to Puppet. In this case, you will want to revoke the host's certificate from the Puppet master. To do this, you can use the clean action:

sudo /opt/puppetlabs/bin/puppet cert clean hostname

The specified host's associated certificates will be removed from Puppet.

View All Signed Requests
If you want to view all of the requests, signed and unsigned, run the following command:
sudo /opt/puppetlabs/bin/puppet cert list --all

You will see a list of all of the requests. Signed requests are preceded by a + and unsigned requests do not have the +.

Output:
+ "puppet"    (SHA256) 5A:71:E6:06:D8:0F:44:4D:70:F0:BE:51:72:15:97:68:D9:67:16:41:B0:38:9A:F2:B2:6C:BB:33:7E:0F:D4:53 (alt names: "DNS:puppet", "DNS:puppet.nyc3.example.com")
+ "host1.nyc3.example.com" (SHA256) F5:DC:68:24:63:E6:F1:9E:C5:FE:F5:1A:90:93:DF:19:F2:28:8B:D7:BD:D2:6A:83:07:BA:FE:24:11:24:54:6A
+ "host2.nyc3.example.com" (SHA256) CB:CB:CA:48:E0:DF:06:6A:7D:75:E6:CB:22:BE:35:5A:9A:B3:93:63:BF:F0:DB:F2:D8:E5:A6:27:10:71:78:DA
+ "ns2.nyc3.example.com" (SHA256) 58:47:79:8A:56:DD:06:39:52:1F:E3:A0:F0:16:ED:8D:40:17:40:76:C2:F0:4F:F3:0D:F9:B3:64:48:2E:F1:CF
Congrats! Your infrastructure is now ready to be managed by Puppet!


Getting Started with Puppet

Now that your infrastructure is set up to be managed with Puppet, we will show you how to use Puppet to do a few basic tasks.
How Facts Are Gathered

Puppet gathers facts about each of its nodes with a tool called facter. Facter, by default, gathers information that is useful for system configuration (e.g. OS names, hostnames, IP addresses, SSH keys, and more). It is possible to add custom facts that aren't part of the default fact set.

The facts gathered can be useful in many situations. For example, you can create an web server configuration template and automatically fill in the appropriate IP addresses for a particular virtual host. Or you can determine that your server's distribution is "CentOS", so you should run the apache2 service instead of httpd. These are basic examples, but they should give you an idea of how facts can be used.

To see a list of facts that are automatically being gathered on your agent node, run the following command:
/opt/puppetlabs/bin/facter

Main Manifest File

Puppet uses a domain-specific language to describe system configurations, and these descriptions are saved to files called "manifests", which have a .pp file extension. The default main manifest file is located on your Puppet master server at /etc/puppetlabs/code/environments/production/manifests/site.pp. Let's create a placeholder file for now:

sudo touch /etc/puppetlabs/code/environments/production/manifests/site.pp

Note that the main manifest is empty right now, so Puppet won't perform any configuration on the agent nodes.

How The Main Manifest Is Executed

The Puppet agent periodically checks in with the Puppet Server (typically every 30 minutes). When it checks in, it will send facts about itself to the master, and pull a current catalog--a compiled list of resources and their desired states that are relevant to the agent, determined by the main manifest. The agent node will then attempt to make the appropriate changes to achieve its desired state. This cycle will continue as long as the Puppet master is running and communicating with the agent nodes.

Immediate Execution on a Particular Agent Node

It is also possible to initiate the check for a particular agent node manually, by running the following command (on the agent node in question):

/opt/puppetlabs/bin/puppet agent --test

Running this will apply the main manifest to the agent running the test. You might see output like the following:

Output:
Info: Using configured environment 'production'
Info: Retrieving pluginfacts
Info: Retrieving plugin
...
Info: Loading facts
Info: Caching catalog for host1
Info: Applying configuration version '1457389302'
Notice: /Stage[main]/Main/File[/tmp/example-ip]/ensure: defined content as '{md5}dd769ec60ea7d4f7146036670c6ac99f'
Notice: Applied catalog in 0.04 seconds

This command is useful for seeing how the main manifest will affect a single server immediately.


One-off Manifests

The puppet apply command allows you to execute manifests that are not related to the main manifest, on demand. It only applies the manifest to the node that you run the apply from. Here is an example:

sudo /opt/puppetlabs/bin/puppet apply /path/to/your/manifest/init.pp

Running manifests in this fashion is useful if you want to test a new manifest on an agent node, or if you just want to run a manifest once (e.g. to initialize an agent node to a desired state).

An Example Manifest

As you may recall, the main manifest file on the Puppet master is located at /etc/puppetlabs/code/environments/production/manifests/site.pp.

On the Puppet master server, edit it now:

sudo vi /etc/puppetlabs/code/environments/production/manifests/site.pp

Now add the following lines to describe a file resource:

file {'/tmp/example-ip':                                            # resource type file and filename

  ensure  => present,                                               # make sure it exists

  mode    => '0644',                                                # file permissions

  content => "Here is my Public IP Address: ${ipaddress_eth0}.\n",  # note the ipaddress_eth0 fact

}

Now save and exit. The inline comments should explain the resource that we are defining. In plain English, this will ensure that all agent nodes will have a file at /tmp/example-ip with -rw-r--r-- permissions, with content that includes the node's public IP address.

You can either wait until the agent checks in with the master automatically, or you can run the /opt/puppetlabs/bin/puppet agent --test command (from one of your agent nodes). Then run the following command to print the file:

cat /tmp/example-ip

You should see output that looks like the following (with that node's IP address):

Output:
Here is my Public IP Address: 128.131.192.11.


Using a Module

Now let's use a module. Modules are useful for grouping tasks together. There are many modules available in the Puppet community, and you can even write your own.

On the Puppet master, install the puppetlabs-apache module from forgeapi:
sudo /opt/puppetlabs/bin/puppet module install puppetlabs-apache

Warning: Do not use this module on an existing Apache setup. It will purge any Apache configurations that are not managed by Puppet.

Now edit site.pp:
sudo vi /etc/puppetlabs/code/environments/production/manifests/site.pp

Now add the following lines to install Apache on host2:

site.pp example
node 'host2' {
  class { 'apache': }             # use apache module
  apache::vhost { 'example.com':  # define vhost resource
    port    => '80',
    docroot => '/var/www/html'
  }
}
# node default {}       # uncomment this line if it doesn't already exist in your manifest

Save and exit. Now the next time Puppet updates host2, it will install the Apache package, and configure a virtual host called "example.com", listening on port 80, and with a document root /var/www/html.

On host2, run the following command:
sudo /opt/puppetlabs/bin/puppet agent --test

You should see a bunch of output indicating that Apache is being installed. Once it is complete, open host2's public IP address in a web browser. You should see a page that is being served by Apache.

Congrats! You have used your first Puppet module!

Conclusion
Now that you have a basic agent/master Puppet installation, you are now ready to learn more about how to use Puppet to manage your server infrastructure. Check out the following tutorial: Getting Started With Puppet Code: Manifests and Modules.