Register forum user name Search FAQ

Gammon Forum

Notice: Any messages purporting to come from this site telling you that your password has expired, or that you need to verify your details, confirm your email, resolve issues, making threats, or asking for money, are spam. We do not email users with any such messages. If you have lost your password you can obtain a new one by using the password reset link.

Due to spam on this forum, all posts now need moderator approval.

 Entire forum ➜ MUSHclient ➜ Bug reports ➜ Enabling another trigger that matches the same regex is ambiguous

Enabling another trigger that matches the same regex is ambiguous

It is now over 60 days since the last post. This thread is closed.     Refresh page


Posted by Kahenraz   (75 posts)  Bio
Date Sun 15 Apr 2018 06:07 AM (UTC)

Amended on Sun 15 Apr 2018 06:50 AM (UTC) by Kahenraz

Message
I often have one trigger enable another to provide a form of cascading behavior for a limited number of runs. For example, I want a certain trigger to fire 3 times but with each run do something different and, if a certain condition is met, stop the cascade.

I had always assumed that enabling one trigger from another trigger would start evaluating the newly enabled one at the NEXT line. And this assumption holds true for all situations where there is a different regex, as no two expression are ever the same, right? Well, not in this case!

Consider the following two triggers.

Name this "Trigger2" and set it to enabled:

^You poke (?P<thing>.+)\.$
..
print("Trigger2")

EnableTrigger("Trigger1")


Name this "Trigger1" and set it to disabled:

^You poke (?P<thing>.+)\.$
..
print("Trigger1")


Copy/paste:

<triggers>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\.$"
   name="Trigger1"
   regexp="y"
   send_to="12"
   variable="Trigger1"
  >
  <send>print("Trigger1")
</send>
  </trigger>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\.$"
   name="Trigger2"
   regexp="y"
   send_to="12"
   variable="Trigger2"
  >
  <send>print("Trigger2")

EnableTrigger("Trigger1")
</send>
  </trigger>
</triggers>


Test case:

You poke a rock.


You might think that the output would be:

Trigger2


As Trigger1 isn't enabled yet. But this isn't the case! You see the following output instead:

Trigger2
Trigger1


This is because Trigger2 is set to "Keep Evaluating" and the other trigger, even though it was just enabled, somehow still gets evaluated on the current line.

So what's the big deal? This is obviously an edge case, right? What's so ambiguous when I just explained everything.

The ambiguity is that this behavior can change due to subtle differences.

For example, swap the names of the triggers so that it's Trigger1 enabling Trigger2 and you will only see one output:

<triggers>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\.$"
   name="Trigger1"
   regexp="y"
   send_to="12"
   variable="Trigger1"
  >
  <send>print("Trigger1")

EnableTrigger("Trigger2")
</send>
  </trigger>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\.$"
   name="Trigger2"
   regexp="y"
   send_to="12"
   variable="Trigger2"
  >
  <send>print("Trigger2")
</send>
  </trigger>
</triggers>


Ok. So it's probably walking through each name in a sorted list. It's the name that is affecting the order, right? Wrong!

Take the first example again and alter the regex of Trigger1 so that it's no longer identical and suddenly it isn't evaluated until the next event:

^You poke (?P<thing>.+)\.$
.. vs ..
^You poke (?P<thing>.+)\.
.. or ..
^(You poke (?P<thing>.+)\.)$


<triggers>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\."
   name="Trigger1"
   regexp="y"
   send_to="12"
   variable="Trigger1"
  >
  <send>print("Trigger1")
</send>
  </trigger>
  <trigger
   enabled="y"
   group="-- Test"
   keep_evaluating="y"
   match="^You poke (?P&lt;thing&gt;.+)\.$"
   name="Trigger2"
   regexp="y"
   send_to="12"
   variable="Trigger2"
  >
  <send>print("Trigger2")

EnableTrigger("Trigger1")
</send>
  </trigger>
</triggers>


The solution to MY problem is to disable "Keep Evaluating" or specify a specific sequence but the bug that I've uncovered is that the order in which triggers fire when enabling one from another where the same line may contain an alternate match is itself ambiguous.

Consider why would you ever WANT one trigger to enable another and have it evaluate the same line... when you could have just performed that action in the first trigger? I see no use case for this.

It is completely acceptable to see this as user error as it is a bug in my logic. But I think it would make more sense for any trigger which is enabled by another delay its activation until the next line is evaluated.
Top

Posted by Nick Gammon   Australia  (23,133 posts)  Bio   Forum Administrator
Date Reply #1 on Sun 15 Apr 2018 07:01 AM (UTC)

Amended on Sun 15 Apr 2018 07:02 AM (UTC) by Nick Gammon

Message
See: http://www.gammon.com.au/forum/?id=6554

Quote:

Match sequence - the order in which triggers are matched is:

First all triggers in the main world file are tested, in trigger sequence. If two triggers have the same sequence number the match order is not defined.


You have two triggers with the same sequence number. The order in which they are evaluated is undefined. If the one which happens to be evaluated first disables the second one, well that is what happens.

The "send to script" is done immediately, and it would be tedious in the extreme to defer things that the script does (like changing the options on another trigger) until all the triggers are evaluated.

- Nick Gammon

www.gammon.com.au, www.mushclient.com
Top

Posted by Kahenraz   (75 posts)  Bio
Date Reply #2 on Sun 15 Apr 2018 07:05 AM (UTC)
Message
Yes, I figured it was some kind of undefined behavior. This post will at least provide some insight for anyone else who may encounter this.
Top

Posted by Fiendish   USA  (2,534 posts)  Bio   Global Moderator
Date Reply #3 on Sun 15 Apr 2018 10:32 PM (UTC)
Message
What a fun find. If I might suggest, you could also have only one trigger and do your logic of what happens when in script space by counting the number of activations.

https://github.com/fiendish/aardwolfclientpackage
Top

The dates and times for posts above are shown in Universal Co-ordinated Time (UTC).

To show them in your local time you can join the forum, and then set the 'time correction' field in your profile to the number of hours difference between your location and UTC time.


13,742 views.

It is now over 60 days since the last post. This thread is closed.     Refresh page

Go to topic:           Search the forum


[Go to top] top

Information and images on this site are licensed under the Creative Commons Attribution 3.0 Australia License unless stated otherwise.