Discussion:
Handling uninstallation upon subordinate removal in reactive
Junien Fridrick
2017-11-21 14:58:15 UTC
Permalink
Hi,

I'm developping a charm, and would like to know the best practive to
do some uninstallation steps when a subordinate gets removed from a
unit (these steps being : uninstall a snap)

The only way I can think of is to use @hook('stop'), but as far as I
remember, using hooks is not something one should do in the reactive
world.

Does anyone have any advice for doing that properly ?

I was also thinking that maybe the snap layer could save which
application installed which snap, and if said application is removed,
then remove said snap. Would that be a good idea ?

Thanks !
--
Juju mailing list
***@lists.ubuntu.com
Modify settings or unsubscribe at: https://lists.ubuntu.c
Dmitrii Shcherbakov
2017-11-21 16:01:54 UTC
Permalink
Hi Junien,

Using hooks in the reactive world is perfectly file - just use them
carefully.

Think of a distinction between the "Juju world" and the "charm world".
Juju's unit agent is an integration point with your charm - the "charm
world" starts when a unit agent runs a charm code and ends when you run a
hook tool (for a moment until returns the result to the charm) or when the
charm process exits. A unit agent (literally) executes a file at
<charmdir>/hooks/<event-name> when an event happens. In most classic
(non-reactive) charms <event-name> is a symlink to <something>_hooks.py -
argument 0 of any executed Linux process will contain that symlink name
instead of a target python file name (e.g. "stop") - this is done so that
charm-helpers can route that to a decorated function @hooks.hook("stop")
via a library shim. This is just routing to the right code within a file.
The same happens with reactive, only the execution path will be unit agent
-> <charmdir>/hooks/<event-name> -> reactive library code -> @hook or
@when* execution.

If you look at any built reactive charm, it will have a generated "hooks"
directory with files that have identical contents for every event name -
they all get you to the reactive library "routing engine" first.

https://git.launchpad.net/telegraf-charm/tree/hooks/hook.template?h=built
https://git.launchpad.net/telegraf-charm/tree/hooks/stop?h=built

This engine then decides what to execute.

Hook template files are provided by layer-basic:

https://charmsreactive.readthedocs.io/en/latest/layer-basic.html#hooks

The "only implements those hooks" restriction comes from the fact that only
certain symlinks are provided and this makes sense to provide those in
layer-basic only as they do not have a relation context.

https://git.io/vFd16

Other hooks are provided as well (again, with just a library entry point)
in subsequent layers (generated via charm-tools when you do `charm build`
based on metadata.yaml):

https://git.launchpad.net/telegraf-charm/tree/hooks/haproxy-relation-joined?h=built

A natural question would be to ask why there are no "install" hook
implementations. This is a trick that most reactive charms use:

1. install event happens;
2. reactive library gets invoked;
3. when_not("installed") gets fired as this state is not set.

You could use any state instead of "installed", like when_not("foobar") and
install packages there - it's just not intuitive. Removal is different as
it is quite explicit (you don't really need a state for it).

Best Regards,
Dmitrii Shcherbakov

Field Software Engineer
IRC (freenode): Dmitrii-Sh

On Tue, Nov 21, 2017 at 5:58 PM, Junien Fridrick <
Post by Junien Fridrick
Hi,
I'm developping a charm, and would like to know the best practive to
do some uninstallation steps when a subordinate gets removed from a
unit (these steps being : uninstall a snap)
remember, using hooks is not something one should do in the reactive
world.
Does anyone have any advice for doing that properly ?
I was also thinking that maybe the snap layer could save which
application installed which snap, and if said application is removed,
then remove said snap. Would that be a good idea ?
Thanks !
--
Juju mailing list
Modify settings or unsubscribe at: https://lists.ubuntu.com/
mailman/listinfo/juju
Tilman Baumann
2017-11-21 16:17:13 UTC
Permalink
Post by Junien Fridrick
remember, using hooks is not something one should do in the reactive
world.
No, just fine. Most of the time when you think hook, reactive will have
a abstract handler for it. But not for all things.

Very simple example
https://github.com/tbaumann/charm-logstash-conf-d/blob/master/reactive/logstash_conf-d.py#L36
Post by Junien Fridrick
Does anyone have any advice for doing that properly ?
I was also thinking that maybe the snap layer could save which
application installed which snap, and if said application is removed,
then remove said snap. Would that be a good idea ?
Totally. At least if you are sure that you where the only one who could
have installed the snap.
--
Juju mailing list
***@lists.ubuntu.com
Modify settings or unsubscribe at: https://lists.ubuntu.com/mailman/listinfo/ju
Stuart Bishop
2017-11-28 00:11:56 UTC
Permalink
On 22 November 2017 at 01:58, Junien Fridrick
Post by Junien Fridrick
I was also thinking that maybe the snap layer could save which
application installed which snap, and if said application is removed,
then remove said snap. Would that be a good idea ?
Your subordinate charm doesn't know it is the only charm using the
snap on that unit, so it is dangerous doing this sort of cleanup.
Well, right now it is pretty safe because snaps in charms are rare but
I expect this to change over time. It is exactly the same as
automatically removing deb packages, which charms rarely if ever do.
Also note that snaps can contain data, and removing them can destroy
this data. subordinates need to tread lightly to avoid victimizing
other charms on the unit, and primary charms don't bother because
removing them means the machine should ideally be rebuilt.

It would be possible to have the snap layer automatically remove
snaps, but the behaviour would need to be explicitly enabled using a
layer.yaml option.
--
Stuart Bishop <***@canonical.com>
--
Juju mailing list
***@lists.ubuntu.com
Modify settings or unsubscribe at: https://lists.ubuntu.com/mailman/listinfo/
Loading...