How To Create A Service In Linux – Linux Systemd Service Unit Configuration

Running a background service in Linux requires understanding systemd or init scripts. If you’ve ever wondered how to create a service in linux, this guide walks you through the entire process step by step.

Services are programs that run in the background, starting automatically at boot. They handle tasks like web servers, databases, or custom scripts. Linux uses systemd as the default service manager on most modern distributions.

Creating your own service isn’t as hard as it sounds. You just need a script, a unit file, and a few commands. Let’s break it down.

What Is A Linux Service

A Linux service is a background process managed by the operating system. It runs independently of user sessions. Services can start, stop, restart, and enable on boot.

Systemd replaced older init systems like SysVinit. It uses unit files with the .service extension. These files define how the service behaves.

Understanding the basics helps you troubleshoot and customize services later. You’ll work with systemctl commands to control them.

Prerequisites For Creating A Service

Before you start, make sure you have:

  • Root or sudo access on your Linux machine
  • A script or program you want to run as a service
  • Basic knowledge of the command line
  • Systemd installed (check with systemctl --version)

Most modern distros like Ubuntu, Debian, Fedora, and CentOS use systemd. If you’re on an older system, you might need to use init scripts instead.

Your script should be executable. Test it manually first to ensure it works.

How To Create A Service In Linux

Now let’s get into the core of this article. This section covers the exact steps for creating a systemd service from scratch.

Step 1: Write Your Script Or Program

Your service needs something to run. It could be a bash script, Python script, or compiled binary. For this example, we’ll use a simple bash script that logs the current time every 10 seconds.

Create a file named /usr/local/bin/myservice.sh:

#!/bin/bash
while true; do
    echo "$(date): Service is running" >> /var/log/myservice.log
    sleep 10
done

Make it executable:

sudo chmod +x /usr/local/bin/myservice.sh

Test it by running the script manually. Press Ctrl+C to stop it.

Step 2: Create A Systemd Unit File

Unit files live in /etc/systemd/system/. Create one named myservice.service:

sudo nano /etc/systemd/system/myservice.service

Add the following content:

[Unit]
Description=My Custom Service
After=network.target

[Service]
ExecStart=/usr/local/bin/myservice.sh
Restart=always
User=nobody
Group=nogroup

[Install]
WantedBy=multi-user.target

Each section has a specific purpose. The [Unit] section describes the service and its dependencies. [Service] defines how it runs. [Install] tells systemd when to start it.

Save and exit the file.

Step 3: Reload Systemd And Enable The Service

After creating the unit file, reload systemd to recognize it:

sudo systemctl daemon-reload

Now enable the service to start at boot:

sudo systemctl enable myservice.service

Start the service immediately:

sudo systemctl start myservice.service

Step 4: Check Service Status

Verify your service is running:

sudo systemctl status myservice.service

You should see output showing “active (running)”. If there are errors, check the logs with journalctl -u myservice.service.

Your service is now running in the background. It will restart automatically if it crashes.

Common Service Directives Explained

Understanding unit file directives helps you customize your service. Here are the most important ones:

  • ExecStart: The command to run when the service starts
  • Restart: When to restart the service (always, on-failure, no)
  • User: The user account under which the service runs
  • Group: The group for the service process
  • WorkingDirectory: Sets the working directory for the service
  • Environment: Sets environment variables
  • After: Specifies dependencies that must start before this service

You can add multiple directives. For example, to set an environment variable:

Environment=MY_VAR=hello

Always test your unit file after making changes. Use systemctl daemon-reload and restart the service.

Managing Your Service With Systemctl

Systemctl is your main tool for controlling services. Here are common commands:

  • sudo systemctl start service-name – Start the service
  • sudo systemctl stop service-name – Stop the service
  • sudo systemctl restart service-name – Restart the service
  • sudo systemctl enable service-name – Enable at boot
  • sudo systemctl disable service-name – Disable at boot
  • sudo systemctl status service-name – Check status
  • sudo systemctl is-active service-name – Check if running

These commands work for any systemd service, not just yours. You can manage built-in services the same way.

Creating A Service That Runs A Python Script

Python scripts are common for services. The process is similar but requires specifying the Python interpreter.

Create a Python script at /usr/local/bin/mypyservice.py:

#!/usr/bin/env python3
import time
import logging

logging.basicConfig(filename='/var/log/mypyservice.log', level=logging.INFO)

while True:
    logging.info('Python service is running')
    time.sleep(10)

Make it executable. Then create a unit file:

[Unit]
Description=Python Service Example
After=network.target

[Service]
ExecStart=/usr/bin/python3 /usr/local/bin/mypyservice.py
Restart=always
User=nobody

[Install]
WantedBy=multi-user.target

Reload and start the service as before. The Python script runs continuously in the background.

Handling Service Logs

Systemd captures stdout and stderr from your service. You can view logs with journalctl:

sudo journalctl -u myservice.service

Add flags for more control:

  • -f to follow new log entries
  • --since "1 hour ago" to filter by time
  • -n 50 to show last 50 lines

You can also configure logging in the unit file. Add StandardOutput=journal or StandardError=journal to control output.

For persistent logs, ensure your service writes to a file or uses syslog.

Service Dependencies And Ordering

Sometimes your service needs another service to be running first. Use the After and Requires directives.

For example, if your service needs MySQL:

[Unit]
Description=My App Service
After=mysql.service
Requires=mysql.service

After only affects ordering. Requires ensures the dependency is active. Combine them for proper behavior.

You can also use Wants for weaker dependencies. The service starts even if the dependency fails.

Environment Variables In Services

Services often need environment variables. Set them in the unit file:

[Service]
Environment=DB_HOST=localhost
Environment=DB_PORT=3306
EnvironmentFile=/etc/myservice/env.conf

Using an environment file keeps sensitive data separate. The file contains lines like KEY=value.

Make sure the file has restricted permissions. Use chmod 600 to protect it.

Testing And Debugging Your Service

If your service doesn’t start, check these common issues:

  • Script permissions: Ensure the script is executable
  • Path errors: Use absolute paths in ExecStart
  • User permissions: The service user must have access to files
  • Syntax errors: Check the unit file with systemd-analyze verify

Use journalctl -xe for detailed error messages. This shows the last few log entries with context.

You can also run the service manually to test:

sudo -u nobody /usr/local/bin/myservice.sh

This simulates how systemd runs the service.

Removing A Service

To remove a service you created:

  1. Stop the service: sudo systemctl stop myservice.service
  2. Disable it: sudo systemctl disable myservice.service
  3. Remove the unit file: sudo rm /etc/systemd/system/myservice.service
  4. Reload systemd: sudo systemctl daemon-reload

Optionally delete the script and log files. This completely removes the service from your system.

Creating A Service With Timers

Systemd timers replace cron jobs. You can create a service that runs on a schedule.

First, create a service unit for the task. Then create a timer unit with the same name but .timer extension.

Example timer file /etc/systemd/system/mytask.timer:

[Unit]
Description=Run mytask daily

[Timer]
OnCalendar=daily
Persistent=true

[Install]
WantedBy=timers.target

Enable and start the timer. The service runs at the scheduled time.

Security Considerations

Running services with root privileges is risky. Always use a dedicated user with minimal permissions.

Set User=nobody or create a system user:

sudo useradd -r -s /bin/false myserviceuser

Then use User=myserviceuser in the unit file.

Restrict file system access with ProtectSystem=strict and ReadWritePaths. This prevents the service from modifying system files.

Use PrivateTmp=true to give the service its own temporary directory.

Advanced Unit File Options

Systemd offers many advanced options:

  • ExecStartPre: Run commands before the main service starts
  • ExecStop: Run commands when the service stops
  • ExecReload: Run commands when reloading the service
  • RestartSec: Wait time before restarting
  • TimeoutStartSec: Maximum time for service to start
  • LimitNOFILE: Maximum number of open files

These options give you fine control over service behavior. Use them as needed for complex services.

Migrating From Init Scripts To Systemd

If you have old init scripts, you can convert them to systemd services. The process involves creating a unit file that calls the init script.

Example unit file for an existing init script:

[Unit]
Description=Legacy Service

[Service]
ExecStart=/etc/init.d/myservice start
ExecStop=/etc/init.d/myservice stop
ExecReload=/etc/init.d/myservice reload
Type=forking

The Type=forking directive tells systemd the service forks into the background. This is common for older daemons.

Test thoroughly after migration. Some init scripts may not work perfectly with systemd.

Common Mistakes And Fixes

Here are frequent errors when creating services:

  • Service not starting: Check permissions and paths
  • Service exits immediately: Use Restart=always and check logs
  • Permission denied: Ensure the user has access to script and logs
  • Unit file not found: Run systemctl daemon-reload
  • Service won’t enable: Check the [Install] section

Most issues are easy to fix. Use systemctl status and journalctl to diagnose.

Frequently Asked Questions

What Is The Difference Between Systemd And Init Scripts?

Systemd is the modern service manager with parallel startup and dependency handling. Init scripts are older shell scripts that run sequentially. Most new Linux distributions use systemd.

Can I Create A Service Without Root Access?

No, creating system services requires root or sudo. However, you can create user services in ~/.config/systemd/user/ that run under your user account.

How Do I Make My Service Restart Automatically?

Add Restart=always or Restart=on-failure to the [Service] section. Systemd will restart the service based on the policy you set.

Why Does My Service Show “Failed” Status?

This usually means the ExecStart command exited with an error. Check the script for bugs, verify permissions, and review logs with journalctl -u servicename.

Can I Run Multiple Instances Of The Same Service?

Yes, use template unit files with @ in the filename. For example, myservice@.service allows you to start instances like myservice@instance1.service.

Conclusion

Learning how to create a service in linux gives you control over background processes. You can automate tasks, run custom applications, and improve system reliability.

Start with a simple script and a basic unit file. Test thoroughly and expand as needed. Systemd provides powerful tools for managing services once you understand the basics.

Remember to always use secure practices. Run services with minimal privileges and monitor logs regularly. With practice, creating services becomes second nature.