Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to fire an event on the condition that a couple of other events have fired at least once? #489

Open
rubenmoor opened this issue Mar 2, 2023 · 0 comments

Comments

@rubenmoor
Copy link

rubenmoor commented Mar 2, 2023

Let's say my website is waiting for two web requests:

evRequest1Done :: Event t () and evRequest2Done :: Event t ()

Now I want an event

evAllRequestsDone :: Event t ()
evAllRequestsDone = waitForAll [evRequest1Done, evRequest2Done]

that fires once all events in the list have fired at least once.

What is the best way to go about this?


I can offer two solutions, both with drawbacks:

Solution 1

EDIT: record instead of sumtype with Semigroup instance

data Done = Done
  { done1 :: Bool
  , done2 :: Bool
  }

setDone1 :: Done -> Done
setDone1 done = done { done1 = True }

setDone2 :: Done -> Done
setDone2 done = done { done2 = True }

waitForAll event1 event2 =
    mapAccumMaybe_ accFunc (Done False False) $
       mergeWith (.) [event1 $> setDone1, event2 $> setDone2]
  where
    accFunc done func =
        let done'@(Done d1 d2) = func done
        in  (Just done', if d1 && d2 then Just () else Nothing)

Disadvantages:

  • record Once required
  • bloated with helper functions (can me mitigated with lenses)
  • gets more bloated for more then two events

Solution 2

waitFor :: Int -> Event t () -> Event t ()
waitFor n event =
    mapAccumMaybe_ accFunc 0 event
  where
    accFunc x y = let z = x + y in (Just z, if z == n then Just () else Nothing)

-- use it like this
waitFor 2 $ mergeWith (+) $ fmap ($> 1) events

Disadvantages:

  • Doesn't actually solve the stated problem, when one of the events in the list can fire more then once
@rubenmoor rubenmoor changed the title How to fire an event on the condition that a couple of other events have fires at least once? How to fire an event on the condition that a couple of other events have fired at least once? Mar 2, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant