0

(Update with more info May 16, see end of post for journalctl messages)

I've created a systemd timer and service with the purpose of running a handful of bash scripts. In particular I'm aimed at mounting an external hdd at a given time, then mounting an veracrypt volume, in order to run some offsite backup actions.

Each of the scripts works correctly when run by my own admin user e.g.

sudo /path/to/script.sh

However, some scripts work and some scripts fail when the systemd service runs. Namely, the mount scripts fail, but the unmount script succeeds.

I'm pretty sure this is either a permissions issue, or a run-as-user issue... but I'm new to systemd, and I can't seem to trace it down. I'd rather avoid using systemctl --user mechanisms, since that relies on a special "linger" type that I'm not familar with... but if that's the only solution, I'll take it.

The high level view of the functions is this...

mountup.timer --> mountup.service --> mountup.sh --> mountusb.sh

A similar workflow is in place for the reverse operation

Here's the code...

/etc/systemd.system/mountup.timer

[Unit]
Description=run the mountup.service on a given schedule

[Timer]
Unit=mountup.service
OnCalendar=*-*-* *:00,30:00
#this means any day, month, year any hour... each 00 and 30 minute
Persistent=true

[Install]
WantedBy=timers.target

/etc/systemd/system/mountup.service

[Unit]
Description = Runs the mountup.sh script

[Service]
Type = simple
User = adminuseraccount
ExecStartPre = /bin/bash -c 'echo "systemctl says...mountup service triggered at $(date)"  >> /usr/local/bin/mountlog.txt'
ExecStart = /usr/local/bin/mountup.sh

/usr/local/bin/mountup.sh

#! /bin/bash

# the fancy function below pipes the echo messages through a function that preprends the timestamp, then sends the output to the logfile

logit() {
    while read
    do
        printf "%(%Y-%m-%d %T)T %s\n" -1 "$REPLY"  >> /usr/local/bin/mountlog.txt
    done
}


#the line below redirects standard output to logfile, along with standard error to the same, 
#after routing them through the fancy function above
exec 3>&1 1>> >(logit) 2>&1

echo "mountup.sh says ... starting mountusb.sh..." &&
/usr/local/bin/mountusb.sh && 
echo "mountup.sh says ... mountusb.sh has been run" &&

/usr/local/bin/mountusb.sh

#! /bin/bash
usbuuid=9743y934y943

mount --uuid $usbuuid  /mnt/targetlocation

Many thanks, I've been at this for about 2 weeks, off and on, and it's finally time to throw in the towel and learn what I'm doing wrong.

Edit: relevant output from sudo journalctl for the mountup.service attempt...

Starting Runs the mountup.sh script...
mountup.service: Control process exited, code=exited, status=1/FAILURE
mountup.service: Failed with result 'exit-code'.
Failed to start Runs the mountup.sh script.

relevant output from sudo journalctl for the mountdown.service attempt...

Starting Runs the mountdown.sh script...
Started Runs the mountdown.sh script.
root : PWD=/ ; USER=root ; COMMAND=/usr/bin/umount /mnt/targetlocation
pam_unix(sudo:session): session opened for user root(uid=0) by (uid=0)
pam_unix(sudo:session): session closed for user root
mountdown.service: Main process exited, code=exited, status=32/n/a
mountdown.service: Failed with result 'exit-code'.

From what I gather, exit code 32 on a umount command simply indicates a failure to unmount a volume, nothing more specific than that.

3
  • "some scripts fail when the systemd service runs": fail in what way? What is logged in the journal when you systemctl start the service? What distribution are you running?
    – larsks
    May 4 at 21:50
  • Any particular reason you're running a script to mount a volume instead of using a mount unit or /etc/fstab? May 6 at 5:51
  • Essentially I was aiming to have the flexibility to edit script actions without messing around in system configuration files. The plan at the moment is to have a nightly timer mount the usb, then mount the volume, and then trigger backup actions. I wanted to be able to edit all of that in one file, rather than having several files in system locations. But, I'm not exactly against using a mount unit... I'm just not familiar with them (haven't really used systemd much yet). But I'd certainly consider alternative suggestions.
    – David
    May 16 at 18:45

1 Answer 1

1

First, you should set a one-shot service, because your scripts exits when it's done:

[Unit]
Description = Runs the mountup.sh script

[Service]
Type = oneshot
User = adminuseraccount
ExecStart = /usr/local/bin/mountup.sh
RemainAfterExit=true
StandardOutput=journal
StandardError=journal

You can then see the output with journalctl -u mountup.service

With the log in the journal, I would also forgo all the redirection of file handles. Plus, your /usr/local/bin/mountlog.txt needs root access to write to. Generally, it's bad practice to write there. But again, I would not use the redirection at all.

And, because you chain commands with &&, you can think about doing set -e. This way, the script aborts on error. There are caveats to that (mis-contructed if-greps could abort your program for instance), but in your case it looks like a good option.

This is not the solution per se, because we don't see the error, but it should help you on your way.

Also, I think I would put it all in one script. Put an 'exit trap' in it to do sync; umount /foo/bar afterwards, so you're sure that when it's done, you have at least flushed file system buffers and the drive is unmounted. This makes it safe to unplug. The reason I tend to call sync in these situations as well, is in case the umount fails.

About umount failure: if that's your/a problem, you may be keeping the location open, if you cd into it, for instance.

3
  • Thanks for your comment, I've edited the question to include the journalctl messages that I could find. I'm definitely open to learning more about the logging features that could help specify the exact problem.
    – David
    May 16 at 20:54
  • Any chance you could take a look at my updates and point me towards a way of identifying the error? I've posted journalctl output that seems relevant, but perhaps there is another command output that would be helpful? @Halfgaar
    – David
    Jun 1 at 18:05
  • @David you haven't tried my suggestions yet, of not using && and not using the output redirection. It's possible that is eating your error messages. Also, I updated my answer with some stuff. Press the 'activity' button to see my edits.
    – Halfgaar
    Jun 1 at 23:13

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .