<div dir="ltr">It does seem that the current behavior of re-evaluating handlers despite none of their flags (states) having changed is confusing, particularly for new users, and we are planning on changing this behavior.  Unfortunately, there are some charms that have come to rely on the current behavior, so we will need to provide some mechanism for getting that behavior, at least for a transition period.  We will also need to provide a mechanism to "force" a flag to be considered "re-activated" even if that's as basic as requiring it be removed and then re-added.</div><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Jul 27, 2017 at 4:13 AM, Alex Kavanagh <span dir="ltr"><<a href="mailto:alex.kavanagh@canonical.com" target="_blank">alex.kavanagh@canonical.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr">Hi<div class="gmail_extra"><br><div class="gmail_quote"><span class="">On Thu, Jul 27, 2017 at 2:37 AM, fengxia <span dir="ltr"><<a href="mailto:fxia1@lenovo.com" target="_blank">fxia1@lenovo.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi Juju,<br>
<br>
Once I set a state, set_state("here"), I want to make sure its @when will only be executed ONCE (when "here" from False->True).<br>
<br>
So my thought is to remove_state("here") in its @when("here") code block. If I don't, will this @when be called multiple times if I don't reset this state? What's the good practice here?</blockquote><div><br></div></span><div>You have a couple of options here depending on the nature of the handler.</div><div><br></div><div><ol><li>If, in the lifetime of the unit's existence, the handler only has to execute ONCE.  (and I mean EVER), then there is a @only_once decorator that can be used.  It can be used in combination with other decorators to set up a condition, but it guarantees that the handler will only be called once.  However, what you probably want is ...<br></li><li>Use a @when_not('flag') and then set it the 'flag' in the body of the handler.</li></ol><div>The first would look something like:</div></div><div><br></div><div>@when('some-condition-flag')</div><div>@only_once</div><div>def do_something_only_once_when_<wbr>some_condition_flag_is_set_<wbr>for_the_first_time():</div><div>     ... do something once ...</div><div><br></div><div>The second treats a flag as a 'have I done this yet' condition, and allows you to reset the flag at some other point in the charm's life cycle so that you can do it again.  'installed' is a good example of this:</div><div><br></div><div>@when_not('installed-<wbr>something')</div><div>def do_install_of_something():</div><div>    ... do the installation ...</div><div>    # when it is fully successful, set the installed-something flag.  Don't set it early as</div><div>    # if it errors, a future handler invocation may be able to continue the installation.</div><div>    set_state('installed-<wbr>something')</div><div><br></div><div><br></div><div>@when(some other conditions indicating do an upgrade)</div><div>def do_upgrade():</div><div>     ... set upgrade sources, or other pre upgrade actions</div><div>     remove_state('installed-<wbr>something')</div><div><br></div><div>In this situation, hopefully you can see that we can re-use 'do_install_of_something()' when we do upgrades.</div><div><br></div><div>I think it's useful to think about states (flags) as being a 'memory' that something has happened, and use them to either gate on not doing things again, or to trigger the next action is a graph of actions that need to take place to get the charm's payload to the desired operational state.  I tend to name them, and use them, to indicate when something has happened, rather than when it hasn't, and so tend to use @when_not('some-flag') on the handler that eventually sets that flag.</div><div><br></div><div>Hope that this helps.</div><div>Alex.</div><span class=""><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><span class="m_-6773860788251545886HOEnZb"><font color="#888888"><br>
<br>
-- <br>
Feng xia<br>
Engineer<br>
Lenovo USA<br>
<br>
Phone: <a href="tel:5088011794" value="+15088011794" target="_blank">5088011794</a><br>
<a href="mailto:fxia1@lenovo.com" target="_blank">fxia1@lenovo.com</a><br>
        <br>
Lenovo.com<br>
Twitter | Facebook | Instagram | Blogs | Forums<br>
<br>
<br>
-- <br>
Juju mailing list<br>
<a href="mailto:Juju@lists.ubuntu.com" target="_blank">Juju@lists.ubuntu.com</a><br>
Modify settings or unsubscribe at: <a href="https://lists.ubuntu.com/mailman/listinfo/juju" rel="noreferrer" target="_blank">https://lists.ubuntu.com/mailm<wbr>an/listinfo/juju</a><br>
</font></span></blockquote></span></div><span class="HOEnZb"><font color="#888888"><br><br clear="all"><div><br></div>-- <br><div class="m_-6773860788251545886gmail_signature" data-smartmail="gmail_signature"><div dir="ltr">Alex Kavanagh - Software Engineer<div>Cloud Dev Ops - Solutions & Product Engineering - Canonical Ltd</div></div></div>
</font></span></div></div>
<br>--<br>
Juju mailing list<br>
<a href="mailto:Juju@lists.ubuntu.com">Juju@lists.ubuntu.com</a><br>
Modify settings or unsubscribe at: <a href="https://lists.ubuntu.com/mailman/listinfo/juju" rel="noreferrer" target="_blank">https://lists.ubuntu.com/<wbr>mailman/listinfo/juju</a><br>
<br></blockquote></div><br></div>