How to Create and Run New Service Units in Systemd Using Shell Script

Few days ago, I came across a Centos 7 32-bit distro and I felt the desire to test it on an old 32-bit machine. After booting I realized that it had a bug and it was loosing the network connection, which I had to turn it “up” manually every time after boot. So, the question was how could I set a script doing this job, running every time I boot my machine?

Well, this is very simple and I ‘ll show you the systemd-way using service units. But first a small introduction to service units.

In this article, I ‘m going to explain what a “service unit” in systemd is, how easy is to create and run one. I will try to simplify what “targets” are, why we call them “collections of units” and what are their “wants”. Finally we are taking advantage of a service unit to run our own script after the boot procedure.

It’s obvious that your computer is useful due to the services it offers and in order to have this functionality, many services have to be called as the computer boots and reaches different levels. Other services are called to be executed when the computer reaches for example the rescue level (runlevel 0) and others when it reaches the multi-user level (runlevel 3). You can imagine these levels as targets.

In a simple way target is a collection of service units. If you want to have a look at service units running in your graphical.target level, type:

# systemctl --type=service
List All Service Units in CentOS 7

List All Service Units in CentOS 7

As you can see some services are active and “running” all the time, while others run one-time and terminate (exited). If you want to check the status of a service, type:

# systemctl status firewalld.service
Check Status of Service in CentOS 7

Check Status of Service in CentOS 7

As you can see I checked the status of firewalld.service (tip: you can use the auto-complete for the name of the service). It informs me that firewalld service is running all the time and it is enabled.

Don’t Miss: How to Configure FirewallD Service in CentOS 7

Enabled and disabled means the service will be permanently loaded or not, during the next boot respectively. On the other hand to start and stop a service has the limitation of the present session and it’s not permanent.

For example, if you type:

# systemctl stop firewalld.service
# systemctl status firewalld.service
Manage Services in CentOS 7

Manage Services in CentOS 7

You can see that the firewalld.service is inactive (dead) but it is still enabled, which means that during next boot it will be loaded. So if we want a service to be loaded during boot time in the future we must enabled it. What a great conclusion! Lets create one, it’s easy.

If you go to the folder:

# cd /etc/systemd/system
# ls -l
SystemD System Files

SystemD System Files

You can see some link files of unit services and some directories of the “wants” of a target. For example: what the multi-user target wants to be loaded when the boot procedure reaches its level, is listed in the directory with name /etc/systemd/system/multi-user.target.wants/.

# ls multi-user.target.wants/
Multi User Targets Services

Multi User Targets Services

As you can see it doesn’t contain only services but also other targets which are also collections of services.

Let’s make a service unit with the name connection.service.

# vim connection.service

and type the following (hit “i” for insert mode), save it and exit (with “esc” and “:wq!” ) :

[Unit]
Description = making network connection up
After = network.target

[Service]
ExecStart = /root/scripts/conup.sh

[Install]
WantedBy = multi-user.target
Create New Service Units in CentOS 7

Create New Service Units in CentOS 7

To explain the above: we have created a unit of service type (you can also create units of target type), we have set it to be loaded after the network.target (you can understand that the booting procedure reaches the targets with a defined order) and we want every-time the service starts to execute a bash script with the name conup.sh which we are going to create.

The fun starts with the last part [install]. It tells that it will be wanted by “multi-user.target”. So if we enable our service a symbolic link to that service will be created inside the multi-user.target.wants folder! Got it? And if we disable it that link will be deleted. So simple.

Just enable it and check:

# systemctl enable connection.service

it informs us that the symbolic link in the multi-user.target.wants folder has been created. Check it:

# ls multi-user.target.wants/
Enable Service in CentOS 7

Enable Service in CentOS 7

As you can see “connection.service” is ready for next booting, but we must create the script file first.

# cd /root
# mkdir scripts
# cd scripts
# vim conup.sh

Add the following line inside vim and save it:

#!/bin/bash
nmcli connection up enp0s3

Of course if you want your script to execute something else, you could type whatever you want instead of the second line.

For example,

#!/bin/bash
touch /tmp/testbootfile

that would create a file inside /tmp folder (just to check that your service is working).

We must also make the script executable:

# chmod +x conup.sh

Now we are ready. If you don’t want to wait until next boot (it’s already enabled) we can start the service for the current session typing:

# systemctl start connection.service

Voila! My connection is up and running!

If you ‘ve chosen to write the command “touch /tmp/testbootfile” inside the script, just to check its functionality, you will see this file created inside /tmp folder.

Confirm Service Status

Confirm Service Status

I really hope to help you figure out what services, wants, targets and running scripts during booting is all about.

Best Affordable Linux and WordPress Services For Your Business
Outsource Your Linux and WordPress Project and Get it Promptly Completed Remotely and Delivered Online.

If You Appreciate What We Do Here On TecMint, You Should Consider:

  1. Stay Connected to: Twitter | Facebook | Google Plus
  2. Subscribe to our email updates: Sign Up Now
  3. Get your own self-hosted blog with a Free Domain at ($3.45/month).
  4. Become a Supporter - Make a contribution via PayPal
  5. Support us by purchasing our premium books in PDF format.
  6. Support us by taking our online Linux courses

We are thankful for your never ending support.

Ioannis Koustoudis

Ioannis Koustoudis is a LFCS­ Linux sysadmin from Kavala, Greece. He works for the ministry of education and supports almost 200 school units in their infrastructure. If he is not in front of a computer screen, he plays music (he is a multi­-instrumentalist) or take care of his two lovely kids.

Your name can also be listed here. Got a tip? Submit it here to become an TecMint author.

RedHat RHCE and RHCSA Certification Book
Linux Foundation LFCS and LFCE Certification Preparation Guide

You may also like...

14 Responses

  1. princeofHack says:

    it’s wrong

    you MUST use /bin/bash /path/myservice.sh.

  2. unnobt says:

    I created a systemd service. But it ask for password every time to start? How to make it run without sudo(ing)?

  3. ksotya says:

    My script doesnt’t start on boot, it starts only after maually typing systemctl start

  4. jagkd705 says:

    What happens when you issue the command?:

    systemctl stop connection.service

    Do you need to supply a stop script definition somewhere or does it just ignore if no stop script is defined?

    • Geert V. says:

      No, it simply stops the service. systemd is taking care of that for you. Note that the service is only stopped for the current session. Once you reboot, the service will be started again (you stopped the service, you didn’t disable it…)

  5. Bruno Silveira says:

    That was an amazing article, very well written and well explained, CONGRATS!
    You should continue writing articles like this one Ioannis, you are really good at it!

  6. Dan St-Andre says:

    I’d love to see a similar article about (1)mounting file systems at boot time, and (2)mounting external drives and media. Specifically, how to alter the default, automatic mount point.

  7. md says:

    What you outline in this article wont work until you run ‘systemctl daemon-reload’. This needs to be done when you add or change unit files.

    • Geert V. says:

      or you reboot. systemd daemon-reload is only needed when you instantaneously want to start the service (which is indeed most of the time what you want…)

  8. Daniel says:

    Could have shared it.. but you spelled systemd wrong in the title. It should not have a capital “D”. You could also have executed a command instead of running a script. It is a good example though.

    • Dan St-Andre says:

      Over the years, I’ve found that wrapping commands with scripts helps make things more maintainable. AND you can do things before and after your command if that is ever needed or wanted.

  9. Fer Nando says:

    Very useful!!!! Thanks so much!!!

  10. Jalal Hajigholamali says:

    Hi,
    Very useful and interesting article,
    Thanks a lot

Got something to say? Join the discussion.

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.