On 07/01/15 07:05, James Powell wrote:
The way I see it is this... Either you have high level dependency handling
within the service supervision system itself, or you have low level dependency
handling within the service execution files.
Keeping the system as simplified as possible lowers the probability and
possibility of issues. That's one of the basic rules of UNIX programming.
I, personally, don't see a need other than low level handling. Systemd/uselessd
even does this within the unit files, as does some instances of
sysvinit/bsdinit by using numbered symlinks for execution order or using a
master control script.
systemd also has 'wants' directories which add dependencies to a unit in
much the way that's being suggested here.
sysvinit obviously has all the LSB headers in the init.d files to try to
express dependencies.
Avery - your suggestion sounds like it ought to be simple to implement
and reasonably easy to understand for a sys-admin. Perhaps the way to go
is to suck it and see - it'll perhaps then be more obvious with a real
implementation if it's worth pursuing.
One small concern would be that it's not enough to simply signal a
dependency to be "up" - it needs to be actually running and working
before you can start the dependent service successfully. To take my
[least-]favourite example, you can't start autofs until ypbind has
actually contacted the NIS server.
Sent from my Windows Phone
________________________________
From: Avery Payne<mailto:[email protected]>
Sent: 1/6/2015 10:35 PM
To: Steve Litt<mailto:[email protected]>
Cc: [email protected]<mailto:[email protected]>
Subject: Re: thoughts on rudimentary dependency handling
On Jan 6, 2015, at 4:56 PM, Steve Litt <[email protected]> wrote:
On Tue, 6 Jan 2015 13:17:39 -0800
Avery Payne <[email protected]> wrote:
On Tue, Jan 6, 2015 at 10:20 AM, Laurent Bercot
<[email protected]
wrote:
I firmly believe that a tool, no matter what it is, should do what
the user wants, even if it's wrong or can't possibly work. If you
cannot do what the user wants, don't try to be smart; yell at the
user, spam the logs if necessary, and fail. But don't do anything
the user has not explicitly told you to do.
And there's the rub. I'm at a crossroad with regard to this because:
1. The user wants service A to run.
2. Service A needs B (and possibly C) running, or it will fail.
Should the service fail because of B and C, even though the user
wants A up,
or
Should the service start B and C because the user requested A be
running?
I thought the way to do the latter was like this:
http://smarden.org/runit/faq.html#depends
If every "upstream" simply declared that his program needs B and C
running before his program runs, it's easy to translate that into an sv
start command in the run script.
Normally, with hand written scripts, that would be the case. You cobble
together what is needed and go on your way. But this time things are a little
different. The project I'm doing uses templates - pre-written scripts that
turn the various launch issues into variables while using the same code. This
reduces development time and bugs - write the template once, debug it once, and
reuse it over and over.
The idea for dependencies is that I could write something that looks at
symlinks in a directory and if the template finds anything, it starts the
dependency. Otherwise it remains blissfully unaware.
The issue that Laurent is arguing for is that by creating such a framework - even one as thin and
as carefully planned - it shuts out future possibilities that would handle this correctly at a very
high level, without the need to write or maintain this layout. To accommodate this possibility and
to maximize compatibility, he is arguing to stay with the same "service is unaware of its
surroundings" that have been a part of the design of all the frameworks - let things fail and
make the admin fix it. There is merit to this, not just because of future expansions, but also
because it allows the end user (read: SysAdmin) the choice of running things. Or long story short,
"don't set policy, let the end user decide". And I agree; I'm a bit old school about
these things and I picked up Linux over a decade ago because I wanted choices.
But from a practical perspective there isn't anything right now that handles dependencies
at a global level. The approach of "minimum knowledge needed and best effort
separation of duty" would give a minimal environment for the time being. The design
is very decentralized and works at a peer level; no service definition knows anything
other than what is linked in its ./needs directory, and side effects are minimized by
trying hard to keep separation of duty. Because the scripts are distributed and meant to
be installed as a whole, I can kinda get away with this because all of the dependencies
are hard coded out of the box and the assumption is that you won't break something by
tinkering with the links. But of course this runs against the setup that Laurent was
discussing. It's also brittle and that means something is wrong with the design. It
should be flexible.
So for now, I will look at having a minimum implementation that starts things as needed.
But only if the user sets a flag to use that feature. This keeps the scripts open for
the future while giving a minimum functionality today that is relatively
"safe". So you don't get dependency resolution unless you specifically turn it
on. And turning it on comes with caveats. It's not a perfect solution, it has potential
issues, and the user abdicates/delegates some of their decisions to my scripts. A no-no,
to be sure. But again, that's the user's choice to flip the switch on...
Also keep in mind that I'm bouncing ideas off of him and he is looking at it from a perspective
much different from mine. I'm taking a pragmatic approach that helps deal with an old situation -
the frameworks would be more usable/adoptable if there was a baseline set of service definitions
that allowed for a wholesale switch over to using them from $(whatever you're using now). So it's
very pragmatic and legacy and "old school" for desktops and servers, and that's something
still needed because we still have those being used everywhere. It's basically a way to
grandfather the frameworks in using the current technology by providing all of the missing
"glue" in the form of service definitions. And unfortunately dependency resolution is an
old issue that has to be worked out as one of my goals, which is to increase ease of use so that
people want to switch. Short version: it's a stop gap measure to do what I am doing. And it will
mostly work but only if I am very, very careful.
Laurent is (I am guessing) looking at this from an angle that includes mobile and embedded devices, slim
provisioned virtual machines, and how "current" system demands are driving Init/services. This is
all bleeding edge "the future of tomorrow is now here today" stuff. It's a different viewpoint and
has different goals. So something will always be slightly off between what I am a doing and what he is doing
- he's waaaay far ahead of me, blazing a trail while I'm fixing up holes in the "here and now".
But it is still important for me to look into the future and realize where things are going. Nothing is
forever and things change. So I need to be prepared.
Hopefully that clears the air a bit with regard to why I am asking and
Laurent's answers. And my apologies in advance to Laurent if I mis-spoke of
his intentions. This is all provided to you based on my current views at this
point in time.