Ticket #31 (closed defect: fixed)

Opened 3 years ago

Last modified 3 years ago

please bless systemd packaging guideliness

Reported by: lennart Owned by: spot
Priority: major Milestone:
Component: Guideline Draft Version:
Keywords: Cc: notting, pmatilai, michich
Blocked By: Blocking:

Change History

comment:1 Changed 3 years ago by lennart

(Note that the top part of the draft should probably be ignored and dropped from the draft when it is accepted. The beef is in the scriptlet suggestions later on)

comment:2 follow-up: ↓ 3 Changed 3 years ago by toshio

Spot's going to take a look at rewriting this so that this is more organized and the language is more like what a packaging guideline should be. Then we can look at whether any of the questions posed in the top section are left unresolved, whether things behave correctly, whether system administrators and packagers will understand how to implement the guidelines, etc.

One thing I think we should add is a section on whether packages should have a sysvinit script and a systemd unit file. Here's an initial suggestion: "A package must not ship both a sysvinit and a systemd unit file installed for use. For packagers wanting to support both, either the sysvinit script can be installed as %doc or the scripts can be in separate subpackages."

comment:3 in reply to: ↑ 2 Changed 3 years ago by spot

Replying to toshio:

One thing I think we should add is a section on whether packages should have a sysvinit script and a systemd unit file. Here's an initial suggestion: "A package must not ship both a sysvinit and a systemd unit file installed for use. For packagers wanting to support both, either the sysvinit script can be installed as %doc or the scripts can be in separate subpackages."

Toshio, the draft already in place talks about providing both sysv initscripts and systemd unit files, so that the sysv initscript can be used as a fallback. This seems to make sense, especially since things like upstart will still be in the repos.

comment:4 Changed 3 years ago by toshio

I just read every place that "sysv" occurs and I still don't see it. Also, i think it doesn't make sense to put both on the filesystem in the normal places as a sysadmin coming from a non-systemd distro (RHEL, Fedora < 15, Ubuntu, Debian, etc) will see the sysv init script and expect it to be in control of the service when in reality, systemd files should be modified to make changes to the behaviour.

comment:5 Changed 3 years ago by spot

Look at the "Naming Units" section. I think we're going to need FESCo to decide whether sysv init scripts should be entirely removed or not.

comment:6 Changed 3 years ago by toshio

If you mean this part:

""" You should name the unit files after the sysv service file name. I.e. /etc/rc.d/init.d/foobar should have its systemd counterpart in /lib/systemd/system/foobar.service. This will enable auomatic fallback in systemd: only if a native file doesn't exist by a specific name it will fall back to the sysv file of the same service. """

I take it to mean, the unit file should have the same name as the sysv script would have had. ie, if we replace apache's sysv init file, we should name the unit file httpd.service to match the sysvinit script. The next paragraphs add an exception to this wherein cross-distro compatibility is meant to trump this.

Whether to remove sysvinit scripts if the package installs a systemd unit file is a "how to package" question so it's a FPC concern, not a fesco concern.

comment:7 Changed 3 years ago by spot

Took me longer than I thought it would, but here's my pass:

https://fedoraproject.org/wiki/TomCallaway/Systemd_Revised_Draft

Note that we'd need to add %{_unitdir} to redhat-rpm-config.

comment:8 Changed 3 years ago by spot

The Bus Activation section is confusing, and no one can figure out what it is supposed to mean, or how it is supposed to work.

comment:9 follow-ups: ↓ 11 ↓ 17 Changed 3 years ago by toshio

I tested this on a not-up-to-date F15 VM and one of my earliest tests didn't work. Updating to latest rawhide before continuing but probably won't get to test more until tomorrow.

Here's what I did

[x] = Setup =
1) Install a SysVinit package
2) Reboot
3) Check that service is not running
4) chkconfig --list service to check that it shouldn't be running

[x] == Variant -- no run sysv ==
4) Upgrade to systemd package
5) Verify that service is not running
6) Reboot
7) Verify that service is not running

== Variant -- running sysv ==
4) chkconfig --levels 345 service on
5) Reboot
6) Verify that service is running
7) Update to systemd package
8) Verify that service is running
[FAIL] systemd did not restart the service with the new code 9) Verify that service is the new version (it echoes the new version back somehow)
10) Reboot
[FAIL] 11) Verify that service is running
Service has a symlink in
/etc/systemd/system/multiuser.target.wants/supervisord.service but it fails to
start  sudo systemctl status supervisord.service says:
Loaded: loaded (service fileanme)
Active: inactive (dead)
CGroup: name=systemd:/system/supervisord.service

# I did not get to the tests below:
1) Install systemd package
2) Check that the package is not running
3) Reboot
4) Verify that the service is not running

[] == Variant -- no run systemd ==
5) Upgrade to second systemd package
6) Verify that service is not running
7) reboot
8) Verify that service is not running

== Variant -- running systemd ==
5) systemctl enable FOO.service
6) Verify that service is not running
7) Reboot
8) Verify that the service is running
9) Upgrade to new systemd package
10) Verify that the service is running
11) Verify that the service is the new version
12) Reboot
13) Verify that the service is running

I also had some questions after experimenting:

just in time starting of services/bus activation?

I thought systemd aimed to do just in time starting of some services like xinetd. The only portion that seems to match that is the bus activation section that is for DBus. Does systemd not do that?

Allow system admins to break services?

Do we want the system administrator to be able to disable a requires= or wants= service? If so, we need to test that it works. (How does this work? For instance, in a pair of fedora packages service nfs requires service portmap. A system administrator installs portmap. They disable portmap. They then install nfs and enable nfs. Should nfs start and automatically start portmap or should nfs try to start and fail because portmap is not running?

Where does systemd log?

I had a hard time debugging some issues because systemd doesn't seem to log failures of services to startup and such. Where does that go to?

comment:10 follow-up: ↓ 12 Changed 3 years ago by laxathom

Lennart,
Did you do any updates on y our side since last FPC meeting?
I saw no changes on draft's page atm.

Let me know so that I can go ahead on dbus part.

comment:11 in reply to: ↑ 9 ; follow-up: ↓ 13 Changed 3 years ago by lennart

Replying to toshio:

I tested this on a not-up-to-date F15 VM and one of my earliest tests didn't work. Updating to latest rawhide before continuing but probably won't get to test more until tomorrow.

Hmm, could you please post proper bugs about the issues you find? Let's keep this ticket about the guidelines only. But anyway:

Here's what I did

> [x] = Setup =
> 1) Install a SysVinit package
> 2) Reboot
> 3) Check that service is not running
> 4) chkconfig --list service to check that it shouldn't be running

The chkconfig glue is only part of chkconfig 1.3.50-1 and newer. Are you sure you had this installed?

Note that we did not actually modify "chkconfig --list" much, since it doesn't really translate to systemd (i.e. runlevels are only supported in a minimal compat way) However, we did add a warning message that that is the case.

> == Variant -- running sysv ==
> 4) chkconfig --levels 345 service on
> 5) Reboot
> 6) Verify that service is running
> 7) Update to systemd package
> 8) Verify that service is running
> [FAIL] systemd did not restart the service with the new code 9) Verify that service is the new version (it echoes the new version back somehow)

Same here.

10) Reboot [FAIL] 11) Verify that service is running Service has a symlink in /etc/systemd/system/multiuser.target.wants/supervisord.service but it fails to start sudo systemctl status supervisord.service says: Loaded: loaded (service fileanme) Active: inactive (dead) CGroup: name=systemd:/system/supervisord.service

Please file a bug about this one and include the output of "systemctl show supervisord.service".

I also had some questions after experimenting:

just in time starting of services/bus activation?

I thought systemd aimed to do just in time starting of some services like xinetd. The only portion that seems to match that is the bus activation section that is for DBus. Does systemd not do that?

systemd can do lazy activation with sockets or bus names. However, doing things lazily is a recipe to make things slow, since you delay execution of everything to the very last moment possible, and often it is much better to do things as early as possible and massively parallel so that the overall startup time is short. So, systemd supports both ideas, the focus is on parallelization though. The lazy starting of things is useful for a few selected packages however, such as CUPS which needs to be started only if a) a printer is plugged in or b) a user actually tries to make use of it, and does not have to be started otherwise at boot.

Note that non-dbus and non-boot activation of services (i.e. based on sockets, hardware and stuff) usually requires upstream support (you need to patch your app, or install udev rules). Hence I see little value listing this in these guidelines which are primarily intended for packagers.

Ideally all these unit files would go upstream anyway. But while for most normal and D-Bus service it is not too bad to maintain them downstream -- for the more complex triggers you definitely want upstream support. And that's documented in daemon(7), but is not directly relevant to Fedora.

Allow system admins to break services?

Do we want the system administrator to be able to disable a requires= or wants= service? If so, we need to test that it works. (How does this work? For instance, in a pair of fedora packages service nfs requires service portmap. A system administrator installs portmap. They disable portmap. They then install nfs and enable nfs. Should nfs start and automatically start portmap or should nfs try to start and fail because portmap is not running?

If you want to disable portmap completely, then you can "mask" it in systemd. For that simply symlink /dev/null to /etc/systemd/system/portmap.service. systemd recognizes that and will list those units as "masked". They cannot be started then, regardless whether manually or automatically. This is a very strong version of disabling services. It's like placing an "exit 0" on top of an init script. Just not ugly.

This feature is supported but it's a bit hidden and we want it to keep it like that. To not confuse the user we will not add "systemctl mask" or "systemctl unmask" to do the /dev/null linking, but expect the user to do that on his own if he wants to. The normal way to disable services should be "systemctl disable" which will still allow manual starting of services but unhooks it from automatic starting on boot, on socket, on bus, on hardware or any other trigger.

But anyway, masking really has nothing to do with the Fedora packaging policy.

Where does systemd log?

I had a hard time debugging some issues because systemd doesn't seem to log failures of services to startup and such. Where does that go to?

To syslog. And during early boot kmsg (i.e. dmesg). Which goes to syslog too. So, the answer is: to syslog.

But anyway, I don't think these points have much to do with the guidelines.

comment:12 in reply to: ↑ 10 Changed 3 years ago by lennart

Replying to laxathom:

Lennart,
Did you do any updates on y our side since last FPC meeting?
I saw no changes on draft's page atm.

I did make quit a number of changes to the part about dbus after I last talked to spot. So from my perspective the current draft should be fine.

comment:13 in reply to: ↑ 11 ; follow-up: ↓ 14 Changed 3 years ago by toshio

Replying to lennart:

Replying to toshio:

I tested this on a not-up-to-date F15 VM and one of my earliest tests didn't work. Updating to latest rawhide before continuing but probably won't get to test more until tomorrow.

Hmm, could you please post proper bugs about the issues you find? Let's keep this ticket about the guidelines only. But anyway:

These bugs deeply affect our ability to approve guidelines. If our tests of packages built using the guidelines fail, we don't know whether they're bugs in the guidelines or bugs in systemd. I can open bugs in bugzilla but we won't be able to approve guidelines until we can run through the guidelines and have the results be what we expect.

comment:14 in reply to: ↑ 13 ; follow-up: ↓ 15 Changed 3 years ago by lennart

Replying to toshio:

Replying to lennart:

Replying to toshio:

I tested this on a not-up-to-date F15 VM and one of my earliest tests didn't work. Updating to latest rawhide before continuing but probably won't get to test more until tomorrow.

Hmm, could you please post proper bugs about the issues you find? Let's keep this ticket about the guidelines only. But anyway:

These bugs deeply affect our ability to approve guidelines. If our tests of packages built using the guidelines fail, we don't know whether they're bugs in the guidelines or bugs in systemd. I can open bugs in bugzilla but we won't be able to approve guidelines until we can run through the guidelines and have the results be what we expect.

Well, but the command lines you chose to test (with explicit runlevel configuration) translate very badly to systemd. I can neither see how this could be relevant for the guidelines in question (they don't mention chkconfig at all), nor to any other guidelines (the existing sysv guidelines don't mention the chkconfig lines you tried).

comment:15 in reply to: ↑ 14 Changed 3 years ago by toshio

Replying to lennart:

Well, but the command lines you chose to test (with explicit runlevel configuration) translate very badly to systemd. I can neither see how this could be relevant for the guidelines in question (they don't mention chkconfig at all), nor to any other guidelines (the existing sysv guidelines don't mention the chkconfig lines you tried).

You appear to be confused about what's being tested. If you read the shorthand notes of what I tested again, remember that when I talk about sysv, I'm talking about installing a package that is using sysvinit scripts, no systemd unit files. When I talk about installing or upgrading to a systemd package I'm talking about upgrading that package to a version that has systemd unit files instead of sysvinit scripts. Does that make it clear that what I'm testing is relevant?

comment:16 Changed 3 years ago by lennart

Can you please paste your supervisor.service file and .spec file?

comment:17 in reply to: ↑ 9 Changed 3 years ago by lennart

Replying to toshio:

Service has a symlink in /etc/systemd/system/multiuser.target.wants/supervisord.service but it fails to

BTW, the name is multi-user.target, not multiuser.target

comment:18 Changed 3 years ago by notting

Initial comment:

The bits about migrating runlevels 0/1/6 should just be removed:

1) Nothing ships a sysv script that hooks into runlevels 0 and 6. (Checked F-14, but I truly don't recall one ever existing) 2) There are two that hook into runlevel 1. Neither of them really should.

More comments in a bit.

comment:19 Changed 3 years ago by toshio

Thought about this a bit -- These are things that the system owners configure. So I think we need to include runlevel 1. Runlevel 0 and 6 probably not since we'd have to be shipping an init script that was meant to be run when the system shuts down.

comment:20 Changed 3 years ago by notting

The idea of single-user/rescue mode is that no services are running. Ergo, I don't see why we'd care about migrating a service from runlevel 1 to rescue.target.

comment:21 Changed 3 years ago by toshio

Because "the user is always right" (read with the same degree of irony as that other well known saying). If a user decides that they need to have gpm run in runlevel 1, then we should migrate that. It's an entirely separate issue from whether we as packagers and os designers would enable the service to start in runlevel 1 when we install the package. In this particular case it's our job to make the system state after a package is upgraded match as closely as possible how the user set it up before the package was upgraded no matter how wrong we might think the user's choices may be.

comment:22 follow-up: ↓ 23 Changed 3 years ago by toshio

I've decided that we should omit runlevel 2 and 4 as well from migration unless someone raises an objection here. Adding them to multi-user since systemd aliases runlevel2,3,4 to multi-user doesn't make much sense. Chances are the user that customized and uses runlevel 2 or 4 doesn't want it to mean the same thing as runlevel 3... they want something custom. So they're just going to have to set up their own custom target to satisfy that.

We should definitely include this in the release notes, though. Added here: https://fedoraproject.org/wiki/Documentation_System_Daemons_Beat

comment:23 in reply to: ↑ 22 Changed 3 years ago by corsepiu

Replying to toshio:

According to inittab runlevel 4 had a more or less well defined meaning: 2 - Multiuser, without NFS (The same as 3, if you do not have networking)

A classical usecase scenario would be an isolated, network-restricted multiheaded-machine or a machine with several (physical) terminals attached to it,

Admitted, this is not a common "desktop user scenario", but is not as uncommon as you may believe.

So they're just going to have to set up their own custom target to satisfy that.

I agree with this reasoning wrt. runlevel 4 (which was undefined), but not wrt. runlevel 2. "networking" and "multiuser" are separate topic and should not be tied together

comment:24 Changed 3 years ago by notting

  • Cc notting added

comment:25 Changed 3 years ago by notting

While runlevel 2 may have a historical meaning, given that runlevel 2 is not *implemented* with that meaning in systemd, doing migrations under the premise that you're giving the admin something similar in runlevel2 seems wrong, and therefore (as Toshio says) shouldn't be done. If the systemd behavior there changes, we could consider possibly handling that case, but if it remains the same, we shouldn't.

comment:26 Changed 3 years ago by toshio

Another datapoint, although runlevel 2 is documented as "multiuser, no networking" in the inittab file, present Fedora packaging doesn't reflect that. grep -i chkconfig /etc/init.d/* and grep -i 'default-start' /etc/init.d/* show a lot of services are not set to on in runlevel 2 even though they are on in runlevel 3 and are not networking related. Also, the latter grep shows that NetworkManager? defaults to starting in runlevel 2 which will bring up the network if any system-wide network configurations are present.

comment:27 Changed 3 years ago by notting

I've been thinking about this... here is an alternate proposal:

Given a systemd service 'foo'

That does not start by default, but can be enabled by the sysadmin:

Requires(post): systemd-units
Requires(preun): systemd-units
Requires(postun): systemd-units

%post
if [ $1 -eq 1 ] ; then 
    # Initial installation 
    /bin/systemctl daemon-reload >/dev/null 2>&1 || :
fi

%preun
if [ $1 -eq 0 ] ; then
    # Package removal, not upgrade
    /bin/systemctl --no-reload disable foo.service > /dev/null 2>&1 || :
    /bin/systemctl stop foo.service > /dev/null 2>&1 || :
fi

%postun
/bin/systemctl daemon-reload >/dev/null 2>&1 || :
if [ $1 -ge 1 ] ; then
    # Package upgrade, not uninstall
    /bin/systemctl try-restart foo.service >/dev/null 2>&1 || :
fi

That does start by default, but can be disabled by the sysadmin:

Requires(post): systemd-units
Requires(preun): systemd-units
Requires(postun): systemd-units

%post
if [ $1 -eq 1 ] ; then 
    # Initial installation 
    /bin/systemctl enable foo.service >/dev/null 2>&1 || :
fi

%preun
if [ $1 -eq 0 ] ; then
    # Package removal, not upgrade
    /bin/systemctl --no-reload disable foo.service > /dev/null 2>&1 || :
    /bin/systemctl stop foo.service > /dev/null 2>&1 || :
fi

%postun
/bin/systemctl daemon-reload >/dev/null 2>&1 || :
if [ $1 -ge 1 ] ; then
    # Package upgrade, not uninstall
    /bin/systemctl try-restart foo.service >/dev/null 2>&1 || :
fi

If a service starts by default, and should not be disabled by the sysadmin, the first set of scriptlets should be used, and the proper links to enable the service should be included in the package. This is a rare case, and is generally only used for things that are part of the boot process. (An example would be the starting of udev.)

Upgrades

There are also the upgrade cases to handle, when your package moves from having SysV scripts to having systemd service files.

Given a systemd service 'foo', and a corresponding SysV service 'bar', packaged in a package named 'baz': (as they do not have to have identical names), we want the following:

On introduction of the systemd service

%triggerun -- baz < <epoch:name-version-release where this scriptlet is introduced>
if  /sbin/chkconfig --level 3 bar >/dev/null 2>&1 ; then
    /bin/systemctl enable foo.service >/dev/null 2>&1
fi
exit 0

When you remove the SysV service from packaging

%triggerun -- baz < <epoch:name-version-release where SysV script was removed>
/sbin/chkconfig --del bar >/dev/null 2>&1 || :

Some notes/rationale:

  1. We check runlevel 3 as that's the common case.
    • Checking runlevels 0, 1 and 6 is nonsensical, as services do not install to them.
    • runlevels 2 and 4 are aliased to 3 in systemd, so installing a separate configuration for those runlevels is not practical; the sysadmin will have to create their own target and migrate as-needed if they are using those runlevels for something different.
    • For runlevel 5, all packages except 1 in an inventory of Fedora 14 have the same settings re: runlevels 3 and 5, so checking runlevel 3 should be sufficient.
  2. We pass '--level' to chkconfig because the upgrade may be running in an environment that does not have the current runlevel set (such as anaconda)
  3. We use triggers so this only runs once to migrate, not constantly on upgrades
  4. Moving SysV services to subpackages is *NOT* recommended, for a couple of reasons:
    1. If the user is using upstart (which is still packaged for the moment) his system will break
    2. Moving the service to the subpackage, and moving the SysV scriptlets with it, will cause havoc with the service's settings due to all the "if [ $1 = 0] " style calculations in the scriptlets not behaving as expected with the package name changing.

comment:28 Changed 3 years ago by notting

This does not currently deal with the fact that 'chkconfig --level' is being forwarded to systemd; that still needs addressed.

comment:29 Changed 3 years ago by toshio

I think these are the ideas being brought up:

triggers -- this was in an early draft[1]_ and fpc decided against it unless necessary. I do not believe there was a vote but the dislike for trigger seemed pretty strong. I brought it back up at a later meeting and the consenus still seemed to be that we should avoid triggers unless there was no other way. If we've gotten to the point where there is no other way, then I will note that notting's trigger scripts include "/sbin/chkconfig --del bar >/dev/null 2>&1
:" which is missing from the early draft.
  • Which runlevels are necessary. I'm still for migrating 1, 3, and 5 because we're migrating user settings, not package defaults. I guess FPC will need to consider both arguments and decide as a whole. Note that like the current drafts, these scriptlets specify --level as an argument to chkconfig which is correct (whereas the early FPC drafts did not specify --level).
  • If I understand the SysV services comment correctly... actually I don't think I understand it correctly. Could you go into more detail about both of the points?

.. _[1]: https://fedoraproject.org/w/index.php?title=TomCallaway/Systemd_Revised_Draft&oldid=214086

comment:30 Changed 3 years ago by notting

Re: triggers

Triggers are more fundamentally correct, and ensure that the operation happens precisely when necessary, and not needlessly on each package upgrade.

Re: sysv services

The basic scriptlets for any SysV service are:

%post
/sbin/chkconfig --add <script>

This sets up chkconfig. Note that this makes the --del in the %post upgrade section of the original draft superfluous, as the links will just come back.

%preun
if [ $1 -eq 0 ] ; then
    /sbin/service <script> stop >/dev/null 2>&1
    /sbin/chkconfig --del <script>
fi

%postun
if [ "$1" -ge "1" ] ; then
    /sbin/service <script> condrestart >/dev/null 2>&1 || :
fi

The tests in this script are testing how many instances of package <whatever> will be either left on the system after the transaction (in case of %preun) or are currently on the system during the transaction (in case of %postun).

Any time you move a script to a different package name (which includes moving it to a subpackage), you end up changing the counting in these scriptlets, as the name of the incoming and outgoing packages no longer match, which means these actions will either fire when they're not supposed to, or *not* fire when they should.

comment:31 follow-up: ↓ 32 Changed 3 years ago by toshio

Will having scriptlets for both init systems in the same package mean that we run try-restart twice on a package?

The scriptlets for sysv are already broken unless we change the package that the systemd unit files are installed via. That's why we need the additional triggerun for removing the sysv scripts if they're dropped separately from the package as a whole.

comment:32 in reply to: ↑ 31 Changed 3 years ago by notting

Replying to toshio:

Will having scriptlets for both init systems in the same package mean that we run try-restart twice on a package?

If it's written that way, yes. If you just call /sbin/service once, the right thing should happen.

The scriptlets for sysv are already broken unless we change the package that the systemd unit files are installed via. That's why we need the additional triggerun for removing the sysv scripts if they're dropped separately from the package as a whole.

The scriptlets do not handle the case where a SysV script is dropped from the package while the package remains installed; this is the same regardless of systemd.

What I'm trying to say is that moving the SysV scripts to a subpackage immediately triggers this, and complicates the accounting for when you might have to add a trigger or other script to clean up.

comment:33 follow-up: ↓ 37 Changed 3 years ago by toshio

If it's only a question of when, immediately is better than deferred because the packager is likely going to reference the guidelines when they add the systemd unit files in order to get things right. If they delete the systemv init scripts from the package at a later date, they are apt to simply stop installing the files rather than reference the systemd page at that point to see what else they should be doing.

comment:34 Changed 3 years ago by lennart

I do believe that Bill's proposal is the one to implement. (And the --level switch is indeed very important for chkconfig, and I hereby offer to fix chkconfig to not forward this to systemd -- though I do wonder how we should best to this? env var? Or --force-sysv switch to chkconfig?)

I would strongly advise against trying to copy over the per-runlevel information as Toshio is suggesting. For a couple of reasons: It maps really badly to systemd, would make it much more complex to understand the contents of /etc/systemd/ due to .wants/ links for legacy names in addition to modern names. Also we do want the new triggers that systemd offers to be used when upgrading: i.e. when bluetooth is upgraded, we want it to be enabled by hw, and no longer by runlevel.

Currently, in daemon(7) from upstream systemd I do recommend Bill's proposal for all distributions (modulo the --level=3 thing, but I fixed that in git). Coming up with a complex transition script that is really difficult to understand would be far from ideal.

So, yeah, I am all for Bill's proposal.

comment:35 follow-up: ↓ 36 Changed 3 years ago by lennart

BTW, other distributions tend to have rpm macros for these service enablement hooks, should we offer the same?This would have the benefit to allow similar rpm spec files even if distributions end up standardizing on slightly different scriptlets.

comment:36 in reply to: ↑ 35 ; follow-up: ↓ 42 Changed 3 years ago by corsepiu

Replying to lennart:

BTW, other distributions tend to have rpm macros for these service enablement hooks,

Could you provide examples/references to these other distro's macros you are referring to?

comment:37 in reply to: ↑ 33 Changed 3 years ago by notting

Replying to toshio:

If it's only a question of when, immediately is better than deferred because the packager is likely going to reference the guidelines when they add the systemd unit files in order to get things right.

It's not just a question of when.

Let's take a sample service, foo. Historically, its SysV service files are in package A. With the introduction of systemd, its systemd service files are in package A', while its SysV service files are in package B.

If A and B are different packages, you need the following scriptlets:

  1. registration of systemd service -> %post of A'
  2. registration of SysV service -> %post of B
  3. deregistration of systemd service -> %preun of A'
  4. deregistration of SysV service -> %preun of B
  5. try-restart of systemd service -> %postun of A'
  6. try-restart of SysV service -> %postun of B
  7. converting SysV state to an initial systemd state on upgrade (assuming split is done at same time) -> %triggerun on A in A'
  8. converting SysV state to new SysV state on upgrade -> %triggerun on A in B
  9. deregistration of earlier SysV service in the case that B is never installed -> %triggerun on A in A'
  10. converting SysV state to an initial systemd state on upgrade (assuming split is *not* done at same time) -> %triggerun on A in A' *and* -> %triggerun on B in A'
  11. some sort of mechanism to get B installed if you need it on upgrade

If we do not move SysV scripts to subpackages, we don't need 7 through 11.

Moreover, trying to have #9 is a bit of a mess... you want the upgrade of A (which has a SysV script) to A' (which has just a systemd script) to do the removal of the older SysV symlinks, but *only* if the new B package isn't also going to be installed. That sounds hard to express in spec-fu.

comment:38 Changed 3 years ago by notting

That should read "If we do not move SysV scripts to subpackages, we don't need 8 through 11."

comment:39 follow-up: ↓ 40 Changed 3 years ago by toshio

You still need 9 when the system v script leaves the main package (whether it is picked up in a subpackage or simply removed). You do not need 8 or 10 or 11 in the subpackage case. We treat the sysv subpackage as a new package that does not share continuity with the old one or the systemd state. Otherwise we'd also eventually end up with packaging guidelines that had to do migrations between initng, minit, et al. That's a path to madness.

I agree that 9 is a mess but it's not that hard to express in a spec file. Package A is only removing the symlinks when you're upgrading from a sysvinit containing package. If B is installed in a later transaction, then there's no problem. So we only care if Package A and Package B are in the same transaction that happens to remove the old package. To do that, in Package B specify a %triggerpostun that runs chkconfig --add when Package A at the old versions is removed.

comment:40 in reply to: ↑ 39 Changed 3 years ago by notting

Replying to toshio:

You seem to be saying that you're intentionally suggesting that SysV scripts be moved to subpackages, and that we do *not* handle any upgrade issues with them.

Why create something broken, rather than just leave them in the main package where they can be handled in a more clean fashion?

comment:41 Changed 3 years ago by toshio

Because it's still not "clean". It just trades one set of issues for another.

comment:42 in reply to: ↑ 36 Changed 3 years ago by lennart

Replying to corsepiu:

Replying to lennart:

BTW, other distributions tend to have rpm macros for these service enablement hooks,

Could you provide examples/references to these other distro's macros you are referring to?

The other day some folks from ALTLinux posted this: http://lists.freedesktop.org/archives/systemd-devel/2011-March/001406.html -- and I believe Suse has something similar in %fillup_and_insserv. And Mandriva in %_post_service. Seems we are the only ones who don't.

comment:43 Changed 3 years ago by lennart

Anything I can do to speed this up?

I really wish we could just agree on notting's proposal and move on.

comment:44 follow-ups: ↓ 45 ↓ 46 Changed 3 years ago by spot

So, there seem to be three issues:

  • 'chkconfig --level' is being forwarded to systemd; that still needs to be addressed. Lennart is going to work on that right now.
  • Handling of runtime levels from old sysv: In speaking with Lennart, it seems as if there is no way to do mappings between runlevels to targets in systemd, and this is an intentional design decision of systemd. I don't think we should spend time trying to work around that.
  • SysV initfiles in subpackages: The reasoning here (from what I recall) was that if an admin comes across a sysv script, he may assume that it is being used and make changes which will never take effect. In speaking with Lennart, he pointed out that the systemctl tool does a few things to minimize this:
  • systemctl status prints the explicit source file for a service
  • systemctl (with no params) prefixes LSB services (checks for LSB header) with "LSB:" and prefixes non-LSB services with "SysV:".

So, IMHO, that is enough to minimize confusion, and we don't need to add complexity by forcing sysv initscripts into subpackages.

* With those three points, and notting's proposed scriptlets, are there any other areas that need improvement?

comment:45 in reply to: ↑ 44 Changed 3 years ago by lennart

Replying to spot:

So, there seem to be three issues:

  • 'chkconfig --level' is being forwarded to systemd; that still needs to be addressed. Lennart is going to work on that right now.

Done. The patch I sent to Bill.

comment:46 in reply to: ↑ 44 Changed 3 years ago by johannbg

  • SysV initfiles in subpackages: The reasoning here (from what I recall) was that if an admin comes across a sysv script, he may assume that it is being used and make changes which will never take effect. In speaking with Lennart, he pointed out that the systemctl tool does a few things to minimize this:
  • systemctl status prints the explicit source file for a service
  • systemctl (with no params) prefixes LSB services (checks for LSB header) with "LSB:" and prefixes non-LSB services with "SysV:".

So, IMHO, that is enough to minimize confusion, and we don't need to add complexity by forcing sysv initscripts into subpackages.

I disagree I think you add confusion and complexity by not separating the sysv initscripts into subpackages after they have been replaced by a native systemd service files + hacks are much more likely to occur as in a systemd service file get written but in that systemd service file the old sysv init script gets called which has couple of few lines added to it ( take firstboot as an example ) which is something I would think is what we dont want to happen.

If an conscious cannot be reached with regards to shipping the old traditional sysv script in a separate package consider moving them out of the init.d directory for example and into a relevant doc directory for the service.

comment:47 Changed 3 years ago by lennart

Folks, can we get this finished? I have prepped the requested script for Spot last an hour after he asked for it, and I have made the necessary chkconfig changes, and they are merged.

Is there anything I can do to speed this up? This has been unresolved for far too long already...

comment:48 Changed 3 years ago by spot

Lennart, Toshio is at PyCon?, and I've been at SXSW. As soon as we get back (next week), we'll try to finish this one up. We're very close to having a solution.

comment:49 Changed 3 years ago by lennart

Ok, I'll try to be patient. ;-)

(I myself will be on PTO the next week though.)

comment:50 Changed 3 years ago by spot

I've documented my testing here:

https://fedoraproject.org/wiki/User:Spot/Testing_systemd

The case where a service is disabled by default, but manually started by the user, then the package is upgraded is failing:

https://fedoraproject.org/wiki/User:Spot/Testing_systemd#Upgrade

The service should be restarted and running in this case, but it is not working. It works as expected on the same system when the sysvinit scripts are used.

I was hopeful that Lennart would be able to figure out what's happening here, but that has not yet happened. It does not seem to make any difference whether we call reload-and-try-restart vs just try-restart in the scriptlet.

comment:51 Changed 3 years ago by spot

Lennart reached out to me this afternoon and is working on this issue, hopefully we'll have a quick resolution and be able to finish testing.

comment:52 Changed 3 years ago by spot

I have now successfully tested disabled by default and enabled by default. Earlier failures are intermittent and not reproducible outside of my VM. Lennart suspects I may have been testing the routine too quickly and triggering its busy loop protection.

Nevertheless, the scriptlets are sound, and this should be ready for a vote on Wednesday.

comment:53 Changed 3 years ago by spot

  • Owner set to spot
  • Status changed from new to assigned

https://fedoraproject.org/wiki/TomCallaway/Systemd_Revised_Draft is approved (+1:5, 0:1, -1:0).

We will work on the Upgrade scriptlets from SysVinit? scripts in the coming week. Lennart officially added /usr/bin/systemd-sysv-convert to a new systemd-sysv subpackage: http://koji.fedoraproject.org/koji/rpminfo?rpmID=2494858

https://fedoraproject.org/wiki/User:Toshio/Systemd_scriptlet_options is the work in progress on that effort.

comment:54 follow-up: ↓ 56 Changed 3 years ago by tibbs

Today on IRC there was a nice flare up about how broken the Systemd_scriptlet_options page is. In that discussion I received this IRC snippet from April 14:

(10:11:47 AM) mezcalero: sgallagh: just wanted to say that the cheat sheet you might have seen on the wiki is not at all correct
(10:11:51 AM) mezcalero: i have fixed that now
(10:11:57 AM) mezcalero: this was mostly toshio going crazy
(10:12:23 AM) mezcalero: also, the script excerpts that toshio was proposing on the wiki to facilitate sysv to systemd uprgades are way over the top if you ask me
(10:12:38 AM) mezcalero: sgallagh: so, what i am suggesting to use you find in the daemon(7) man page
(10:12:41 AM) mezcalero: and is much much simpler
(10:13:00 AM) mezcalero: have a look there, it contains rpm example scriptlets to cover upgrades
(10:13:08 AM) mezcalero: i think it doesn't get much simpler than that in the end
(10:13:45 AM) mezcalero: sgallagh: if you have any questions, please ping me
(10:13:56 AM) mezcalero: sgallagh: most of these things are actually very well documented
(10:14:05 AM) mezcalero: but there's a lot of non-sensical stuff found on the wiki

So I guess the claim is that we should start over. This is what we're supposed to be using:

   %triggerun -- sssd < 1.5.5-5
    if /sbin/chkconfig --level 3 sssd ; then
    /bin/systemctl --no-reload enable sssd.service >/dev/null 2>&1 || :
    fi
     
    if /sbin/chkconfig --level 5 sssd ; then
    /bin/systemctl --no-reload enable sssd.service >/dev/null 2>&1 || :
    fi

But that confuses me quite a bit, because I thought systemd-sysv-convert is what Lennart wanted us to use. Are we supposed to just copy from the daemon(7) manpage instead? Does that single triggerun script cover all of the bases? Note that it did break my F15 machine (no sssd on boot, needed systemctl enable sssd.service to get it working again) but that is probably due to my having gotten a bad sssd update at some point in the past.

comment:55 Changed 3 years ago by tibbs

Also, it occurs to me that someone may want to make a blanket announcement that folks shouldn't be transitioning packages from sysv to systemd, if indeed folks shouldn't be doing that. Somebody's been filing bugs against piles of services; here's one: https://bugzilla.redhat.com/show_bug.cgi?id=689853

comment:56 in reply to: ↑ 54 ; follow-up: ↓ 57 Changed 3 years ago by notting

Replying to tibbs:

So I guess the claim is that we should start over. This is what we're supposed to be using:

   %triggerun -- sssd < 1.5.5-5
    if /sbin/chkconfig --level 3 sssd ; then
    /bin/systemctl --no-reload enable sssd.service >/dev/null 2>&1 || :
    fi
     
    if /sbin/chkconfig --level 5 sssd ; then
    /bin/systemctl --no-reload enable sssd.service >/dev/null 2>&1 || :
    fi

But that confuses me quite a bit, because I thought systemd-sysv-convert is what Lennart wanted us to use. Are we supposed to just copy from the daemon(7) manpage instead? Does that single triggerun script cover all of the bases? Note that it did break my F15 machine (no sssd on boot, needed systemctl enable sssd.service to get it working again) but that is probably due to my having gotten a bad sssd update at some point in the past.

My reading of the bits in the scriptlet options page that aren't in daemon(7) (splitting them for easier commenting):

%triggerun -- httpd < 1.0-2
/usr/bin/systemd-sysv-convert --save httpd

AFAIK, systemd-sysv-convert was intended to be an optional step for admins to follow. In that case, making calling it a required part of scriptlets seems overkill.

%triggerun -- httpd < 1.0-2
/sbin/chkconfig --del httpd >/dev/null 2>&1 || :

This isn't in daemon(7) because it's tied to when the SysV init script would be removed from the package, not the presence of a systemd service file. It is always required in a package when a SysV script is removed from it while the package remains installed; it's an orthogonal problem to anything with systemd (other than systemd may be the cause of why the SysV script is removed).

%triggerun -- httpd < 1.0-2
/bin/systemctl try-restart apache-httpd.service >/dev/null 2>&1 || :

I do not believe this is needed; the %postun of the SysV package you're upgrading from will still call 'service <foo> condrestart', which will redirect correctly (as long as the SysV and systemd services have the same name).

%triggerun -- httpd < 1.0-2
/bin/systemctl daemon-reload >/dev/null 2>&1 || :

This is already covered in the %post, so I'm not sure why it would be needed here.

# If we're shipping sysvinit scripts
%triggerpostun -n httpd-sysvinit -- httpd < 1.0-2
/sbin/chkconfig --add httpd >/dev/null 2>&1 || :

This seems drastically underexplained here - why would the sysvinit scripts be in a subpackage? Furthermore, given the previous triggers that may call --del, it may not function correctly; I don't know that there's explicit ordering guaranteed here.

comment:57 in reply to: ↑ 56 ; follow-up: ↓ 59 Changed 3 years ago by spot

Replying to notting:

%triggerun -- httpd < 1.0-2
/usr/bin/systemd-sysv-convert --save httpd

AFAIK, systemd-sysv-convert was intended to be an optional step for admins to follow. In that case, making calling it a required part of scriptlets seems overkill.

No, you're really misunderstanding things here. systemd-sysv-convert is a python script which does two things:

--save : Saves the existing state of the sysv enablement levels in a file. Does not apply that state to the systemd configuration. -- : Applies the saved state of the sysv enablement levels from disk to the systemd configuration.

By not calling systemd-sysv-convert --save, that state is lost, so any admin who made customizations will not be able to trivially apply the same enablement levels to the systemd configuration. Saving this state is the correct thing to do. (Toshio originally advocated that we force the migration of enablement levels, but he was alone in that opinion.)

%triggerun -- httpd < 1.0-2
/sbin/chkconfig --del httpd >/dev/null 2>&1 || :

This isn't in daemon(7) because it's tied to when the SysV init script would be removed from the package, not the presence of a systemd service file. It is always required in a package when a SysV script is removed from it while the package remains installed; it's an orthogonal problem to anything with systemd (other than systemd may be the cause of why the SysV script is removed).

The approved (but not yet written up guidelines) require the SysV init script to be moved into a subpackage, if it is retained at all. So as part of the migration, the SysV init script is either removed entirely or put in a subpackage, hence this line.

%triggerun -- httpd < 1.0-2
/bin/systemctl try-restart apache-httpd.service >/dev/null 2>&1 || :

I do not believe this is needed; the %postun of the SysV package you're upgrading from will still call 'service <foo> condrestart', which will redirect correctly (as long as the SysV and systemd services have the same name).

I'm not sure we can assume they will have the same name. In the example used, the names are not identical. This is harmless in the best case, necessary in the worst case.

%triggerun -- httpd < 1.0-2
/bin/systemctl daemon-reload >/dev/null 2>&1 || :

This is already covered in the %post, so I'm not sure why it would be needed here.

Not sure about this one. We can test without it.

# If we're shipping sysvinit scripts
%triggerpostun -n httpd-sysvinit -- httpd < 1.0-2
/sbin/chkconfig --add httpd >/dev/null 2>&1 || :

This seems drastically underexplained here - why would the sysvinit scripts be in a subpackage? Furthermore, given the previous triggers that may call --del, it may not function correctly; I don't know that there's explicit ordering guaranteed here.

Because the new guidelines require SysV init scripts to be in a subpackage (or not packaged at all)?

comment:58 Changed 3 years ago by spot

Whoops. That first part should say:

--save : Saves the existing state of the sysv enablement levels in a file. Does not apply that state to the systemd configuration.

--show : Show saved SysV runlevel information for one or more services

--apply : Applies the saved state of the sysv enablement levels from disk to the systemd configuration.

comment:59 in reply to: ↑ 57 ; follow-up: ↓ 60 Changed 3 years ago by notting

Wow, trac's quoting is awful.

No, you're really misunderstanding things here. systemd-sysv-convert is a python script which does two things:

--save : Saves the existing state of the sysv enablement levels in a file. Does not apply that state to the systemd configuration. -- : Applies the saved state of the sysv enablement levels from disk to the systemd configuration.

By not calling systemd-sysv-convert --save, that state is lost, so any admin who made customizations will not be able to trivially apply the same enablement levels to the systemd configuration. Saving this state is the correct thing to do. (Toshio originally advocated that we force the migration of enablement levels, but he was alone in that opinion.)

If it's trivial to correctly apply, it should be automatic. If it's not trivial to correctly apply (which is the implication here), why have an entirely separate tool or scriptlet as opposed to just 'chkconfig --list $foo > /var/log/$foo.state'? (or similar)

The approved (but not yet written up guidelines) require the SysV init script to be moved into a subpackage, if it is retained at all. So as part of the migration, the SysV init script is either removed entirely or put in a subpackage, hence this line.

I still think subpackaging of scriptlets is a really bad idea (excess complication for little gain). See later.

%triggerun -- httpd < 1.0-2
/bin/systemctl try-restart apache-httpd.service >/dev/null 2>&1 || :

I do not believe this is needed; the %postun of the SysV package you're upgrading from will still call 'service <foo> condrestart', which will redirect correctly (as long as the SysV and systemd services have the same name).

I'm not sure we can assume they will have the same name. In the example used, the names are not identical. This is harmless in the best case, necessary in the worst case.

We can require that people create separate subpackages when they migrate, but can't require that files that they're creating are named a particular way? Seems arbitrary.

Note that in this case you could just have a /lib/systemd/system/httpd.service symlink to apache-httpd.service, and it would work, without complications.

# If we're shipping sysvinit scripts
%triggerpostun -n httpd-sysvinit -- httpd < 1.0-2
/sbin/chkconfig --add httpd >/dev/null 2>&1 || :

This seems drastically underexplained here - why would the sysvinit scripts be in a subpackage? Furthermore, given the previous triggers that may call --del, it may not function correctly; I don't know that there's explicit ordering guaranteed here.

Because the new guidelines require SysV init scripts to be in a subpackage (or not packaged at all)?

OK, but that policy doesn't make it work with respect to ordering of other triggers. (Not subpackaging avoids this problem.)

comment:60 in reply to: ↑ 59 ; follow-up: ↓ 61 Changed 3 years ago by spot

Replying to notting:

Wow, trac's quoting is awful.

Yes. Yes it is.

If it's trivial to correctly apply, it should be automatic. If it's not trivial to correctly apply (which is the implication here), why have an entirely separate tool or scriptlet as opposed to just 'chkconfig --list $foo > /var/log/$foo.state'? (or similar)

Look at what /usr/bin/systemd-sysv-convert actually does (it lives in the systemd-sysv subpackage). It is a little more complicated (and cleaner) than scraping chkconfig.

The approved (but not yet written up guidelines) require the SysV init script to be moved into a subpackage, if it is retained at all. So as part of the migration, the SysV init script is either removed entirely or put in a subpackage, hence this line.

I still think subpackaging of scriptlets is a really bad idea (excess complication for little gain). See later.

I strongly disagree (as does the FPC). If we're moving to systemd, we should move. I honestly feel that keeping sysv initscripts around in the main package is just a recipe for confusing people who come across both the systemd unit file and the sysv initscript. Really, we want everyone to be using systemd unit files, and only have the sysv initscripts for use cases that do not involve systemd.

We can require that people create separate subpackages when they migrate, but can't require that files that they're creating are named a particular way? Seems arbitrary.

Some of the old names are bad. This is an excellent time to fix that.

Note that in this case you could just have a /lib/systemd/system/httpd.service symlink to apache-httpd.service, and it would work, without complications.

Sure, and you can carry that symlink forever (hoping that someone doesn't break/remove it at some point), or you can have one scriptlet line to cover the case. I know which I'd prefer.

OK, but that policy doesn't make it work with respect to ordering of other triggers. (Not subpackaging avoids this problem.)

Well, be specific on what is broken here, because we're either subpackaging sysv initscripts or not packaging them at all.

comment:61 in reply to: ↑ 60 ; follow-up: ↓ 62 Changed 3 years ago by notting

Replying to spot:

Look at what /usr/bin/systemd-sysv-convert actually does (it lives in the systemd-sysv subpackage). It is a little more complicated (and cleaner) than scraping chkconfig.

Fair enough. I just wonder if it's a solution in search of a problem - as you state later, it's one of those things that will need carried forward for quite a period of time, and are we sure people would really need a tool for this use case, rather than just documenting how admins can enable/disable services when necessary? For example, do we then need to localize this tool? Offer a GUI version? etc.

I still think subpackaging of scriptlets is a really bad idea (excess complication for little gain). See later.

I strongly disagree (as does the FPC). If we're moving to systemd, we should move. I honestly feel that keeping sysv initscripts around in the main package is just a recipe for confusing people who come across both the systemd unit file and the sysv initscript. Really, we want everyone to be using systemd unit files, and only have the sysv initscripts for use cases that do not involve systemd.

Then drop the scripts and don't subpackage them - I have no problem with that. My sole issue is with subpackaging of the scripts - it's essentially creating complication merely to support a 'choice' (booting with some other init daemon) that we don't regularly support or test (in which case, it's not a good choice to support at all.)

Note that in this case you could just have a /lib/systemd/system/httpd.service symlink to apache-httpd.service, and it would work, without complications.

Sure, and you can carry that symlink forever (hoping that someone doesn't break/remove it at some point), or you can have one scriptlet line to cover the case. I know which I'd prefer.

'Hoping that someone doesn't break it'? I think future-proofing against admins removing packaged files from the system is probably out-of-scope for packaging guidelines. (And, in any case, it would get 'fixed' in the next package update.)

Perhaps phrase it as:

If the systemd service file has a different name than the SysV service, you can either

1. Add a /lib/systemd/system/<old-name>.service symlink to the new service file.
2. Add this trigger as specified:

This is something that the packager should be able to obviously determine, and implement appropriately.

OK, but that policy doesn't make it work with respect to ordering of other triggers. (Not subpackaging avoids this problem.)

Well, be specific on what is broken here, because we're either subpackaging sysv initscripts or not packaging them at all.

You've got separate %triggerpostun scriptlets in your example, one that does --del (in the main package), and one that does --add (in the subpackage). This relies on them being ordered properly to actually do what you want, and I don't think that ordering is guaranteed anywhere.

comment:62 in reply to: ↑ 61 ; follow-up: ↓ 63 Changed 3 years ago by spot

Replying to notting:

Fair enough. I just wonder if it's a solution in search of a problem - as you state later, it's one of those things that will need carried forward for quite a period of time, and are we sure people would really need a tool for this use case, rather than just documenting how admins can enable/disable services when necessary? For example, do we then need to localize this tool? Offer a GUI version? etc.

For those people who have customized their runlevels, it will be a useful tool. For people who notice the changes in startup items after an upgrade, and what to know why, it will be a useful tool. I prefer to cover those cases. As to localization/GUI, well, I'm sure Lennart accepts patches.

Then drop the scripts and don't subpackage them - I have no problem with that. My sole issue is with subpackaging of the scripts - it's essentially creating complication merely to support a 'choice' (booting with some other init daemon) that we don't regularly support or test (in which case, it's not a good choice to support at all.)

I'm not opposed to this approach, but I think we'd want to run that by FESCo, as we would make it impossible for a Fedora spin that used upstart, for example.

Perhaps phrase it as:

If the systemd service file has a different name than the SysV service, you can either

1. Add a /lib/systemd/system/<old-name>.service symlink to the new service file.
2. Add this trigger as specified:

This is something that the packager should be able to obviously determine, and implement appropriately.

I don't have an issue with that approach.

You've got separate %triggerpostun scriptlets in your example, one that does --del (in the main package), and one that does --add (in the subpackage). This relies on them being ordered properly to actually do what you want, and I don't think that ordering is guaranteed anywhere.

Even if the subpackage always Requires the base package?

comment:63 in reply to: ↑ 62 ; follow-up: ↓ 71 Changed 3 years ago by notting

  • Cc pmatilai added

Replying to spot:

For those people who have customized their runlevels, it will be a useful tool. For people who notice the changes in startup items after an upgrade, and what to know why, it will be a useful tool. I prefer to cover those cases. As to localization/GUI, well, I'm sure Lennart accepts patches.

But it's a niche tool as currently specified/implemented - it only handles changes across sysv -> systemd upgrades. It only handles cases where a user enabled a service in sysv that is currently disabled, not the reverse. It doesn't integrate into either systemctl-gtk, or chkconfig/ntsysv. It operates on disparate legacy runlevelX targets, despite the fact that many of them map to the same place in systemd. My concern is just if this is The Way (documented as all packages Must Use This), it doesn't seem to be the best designed way.

I'm not opposed to this approach, but I think we'd want to run that by FESCo, as we would make it impossible for a Fedora spin that used upstart, for example.

It wouldn't make it impossible; see the initng-ifiles package currently in Fedora for a solution to this approach. (It may certainly make it *harder*, but I don't feel that that's necessarily a bad thing.)

You've got separate %triggerpostun scriptlets in your example, one that does --del (in the main package), and one that does --add (in the subpackage). This relies on them being ordered properly to actually do what you want, and I don't think that ordering is guaranteed anywhere.

Even if the subpackage always Requires the base package?

CC'ing Panu - I don't think that affects ordering, but he'd be able to state for sure.

comment:64 Changed 3 years ago by spot

Migration guidelines (with omission of scriptlet dealing with sysv initscript subpackage) were approved at the 2011-04-27 meeting.

Announcement text:

A new set of guidelines have been written for handling systemd in packages:

https://fedoraproject.org/wiki/Packaging:Guidelines:Systemd https://fedoraproject.org/wiki/Packaging:ScriptletSnippets#Systemd

comment:65 Changed 3 years ago by spot

  • Status changed from assigned to closed
  • Resolution set to fixed

comment:66 Changed 3 years ago by lennart

  • Status changed from closed to reopened
  • Resolution fixed deleted

Sorry, I have no idea how I missed the further discussions. But I don't really like the now approved upgrade snippets:

A) they do not take into account whether a service was previously enabled, instead services are always enabled or always disabled on upgrade. There should really be a test with chkconfig to take into account the previous enablement state.

B) There are two reloads in the trigger: one implicit one in the "systemctl enable" call, and one explicit one. Use --no-reload on the enable. (I am understanding right that the new %postun would not be executed on upgrade from the sysv version to the systemd version, right, because always the %postun of the installed package version is run?)

C) systemctl daemon-reload is run after the try-restart. Thus the try-restart would use the old config data, not the new.

Removing the sysv scripts when transitioning sounds good to me.

This is what I propose:

%triggerun -- httpd < 1.0-2
/usr/bin/systemd-sysv-convert --save httpd
if /sbin/chkconfig --level 5 httpd ; then
        /bin/systemctl --no-reload enable httpd.service >/dev/null 2>&1 ||:
fi
/sbin/chkconfig --del httpd >/dev/null 2>&1 ||:
/bin/systemctl daemon-reload >/dev/null 2>&1 ||:
/bin/systemctl try-restart httpd.service >/dev/null 2>&1 ||:

Why test against runlevel 5? Because it is the most featureful. Usually a superset of the others.

The try-restart is optional.

comment:67 Changed 3 years ago by lennart

Actually, the chkconfig --del includes an implicit daemon-reload, too, so the explicit daemon-reload line can be removed:

%triggerun -- httpd < 1.0-2
/usr/bin/systemd-sysv-convert --save httpd
if /sbin/chkconfig --level 5 httpd ; then
        /bin/systemctl --no-reload enable httpd.service >/dev/null 2>&1 ||:
fi
/sbin/chkconfig --del httpd >/dev/null 2>&1 ||:
/bin/systemctl try-restart httpd.service >/dev/null 2>&1 ||:

comment:68 follow-up: ↓ 70 Changed 3 years ago by notting

Note that (as stated above) the 'try-restart' command is only needed in the trigger if it's a different service name than the SysV script. If it's the same, the %postun of the prior package will handle it (and, in fact, cause the service to get bounced twice if this is in the trigger.)

comment:69 Changed 3 years ago by lennart

Actually, the --save line needs protection for
: too:
%triggerun -- httpd < 1.0-2
/usr/bin/systemd-sysv-convert --save httpd >/dev/null 2>&1 ||:
if /sbin/chkconfig --level 5 httpd ; then
        /bin/systemctl --no-reload enable httpd.service >/dev/null 2>&1 ||:
fi
/sbin/chkconfig --del httpd >/dev/null 2>&1 ||:
/bin/systemctl try-restart httpd.service >/dev/null 2>&1 ||:

comment:70 in reply to: ↑ 68 Changed 3 years ago by lennart

Replying to notting:

Note that (as stated above) the 'try-restart' command is only needed in the trigger if it's a different service name than the SysV script. If it's the same, the %postun of the prior package will handle it (and, in fact, cause the service to get bounced twice if this is in the trigger.)

If the service name changes while upgrading, then the new service will not be running and hence the try-restart be a NOP.

comment:71 in reply to: ↑ 63 Changed 3 years ago by pmatilai

Replying to notting:

You've got separate %triggerpostun scriptlets in your example, one that does --del (in the main package), and one that does --add (in the subpackage). This relies on them being ordered properly to actually do what you want, and I don't think that ordering is guaranteed anywhere.

Even if the subpackage always Requires the base package?

CC'ing Panu - I don't think that affects ordering, but he'd be able to state for sure.

Sorry for the late response, been half-dead with a flu this week :-/

Of course requires affect ordering: package's dependencies need to be installed before the package itself, otherwise practically nothing at all would work. This is guaranteed too, except when the packages are involved in dependency loop(s) at which point it's a best-effort situation as no guarantees can be made.

So if the sub-package requires the base package and base package does NOT require the sub-package (directly or indirectly), then it's guaranteed that base package gets installed before the sub-package (and reverse for erasure).

comment:72 Changed 3 years ago by notting

Even if B is ordered after A, does that mean if A and B both have triggers on C's uninstall, that A's trigger will fire before B?

comment:73 Changed 3 years ago by sundaram

If this is getting revised again, please let use macros along the lines of

http://lists.freedesktop.org/archives/systemd-devel/2011-March/001406.html

All the other mainstream distributions use macros for such purposes. It is annoying if package maintainers have to tweak the scriplets everytime a packaging guideline on this change. Macros would shield us from having to micro manage changes.

comment:74 Changed 3 years ago by michich

  • Cc michich added

comment:75 follow-up: ↓ 76 Changed 3 years ago by spot

The conditionalization of the enablement line isn't valid. FESCo determines what services get to autostart, and packagers will enable that accordingly, not based on an arbitrary runlevel. The other changes make sense, and since they're just cleanups (and because it gives me migraines to work with systemd scriptlets), I've just made those changes.

comment:76 in reply to: ↑ 75 Changed 3 years ago by michich

Replying to spot:

The conditionalization of the enablement line isn't valid. FESCo determines what services get to autostart, and packagers will enable that accordingly, not based on an arbitrary runlevel.

Therefore any migration of a package from an initscript to a systemd service will always result in a reset of the service's enabled/disabled state (does it not worry FESCo?). I liked the idea with inheriting the state from a selected runlevel better, but so be it. As long as the result is understood by everyone. For this reason a few things should be added:

  • Packages must be strictly forbidden from migrating to systemd within updates to a Fedora release. The migration is only allowed between Fedora releases. The scriptlet guideline "Packages migrating to a systemd unit file from a SysV initscript" should stress that.
  • The release notes should have a big warning like:

After an upgrade from a previous Fedora release, some services that were disabled may get enabled and vice-versa. Make sure you check them and fix them yourself as needed. List of services to check: ...

Such a warning will be probably needed for several more Fedora releases, depending on how long it will take for all packages to migrate.

comment:77 Changed 3 years ago by spot

Alert note amendment approved (+1:7, 0:0, -1:0)

comment:78 Changed 3 years ago by spot

  • Status changed from reopened to closed
  • Resolution set to fixed

Warning added.

Note: See TracTickets for help on using tickets.