purescripthalogen

Purescript Halogen DeepPeek Child Instead of Grandchild


I'm trying to adapt this example https://github.com/slamdata/purescript-halogen/blob/v0.12.0/examples/deep-peek/src/Main.purs#L58 (relevant part copied below), but instead of peeking the grandchild I just want to peek the child, or in this case peekList. I also want to keep the slot type as a parameter in the peek function for peekList.

peek :: forall a. H.ChildF ListSlot ListQueryP a -> H.ParentDSL State (ListStateP g) Query ListQueryP g ListSlot Unit
peek = coproduct peekList peekTicker <<< H.runChildF

peekList :: forall a. ListQuery a -> H.ParentDSL State (ListStateP g) Query ListQueryP g ListSlot Unit
peekList _ =
  -- we're not actually interested in peeking on the list.
  -- instead of defining a function like this, an alternative would be to use
  -- `(const (pure unit))` in place of `peekList` in the `coproduct` function
  pure unit

peekTicker :: forall a. H.ChildF TickSlot TickQuery a -> H.ParentDSL State (ListStateP g) Query ListQueryP g ListSlot Unit
peekTicker (H.ChildF _ (Tick _)) = H.modify (\st -> { count: st.count + 1 })
peekTicker _ = pure unit

How can I actually peek peekList without losing the slot parameter?

I've tried removing the H.runChildF:

peek = coproduct peekList (const (pure unit))

and then adding back in the slot parameter to peekList:

peekList :: forall a. H.ChildF ListSlot ListQuery a -> H.ParentDSL State (ListStateP g) Query ListQueryP g ListSlot Unit

But then in peek I get the error "Could not match type ChildF with type Coproduct while trying to match type ChildF ListSlot with type Coproduct (ChildF ListSlot ListQuery)"

If I just try to use peekList instead o peek, i get the error "Could not match type Coproduct ListQuery (ChildF TickSlot TickQuery) with type ListQuery while trying to match type ChildF ListSlot (Coproduct ListQuery (ChildF TickSlot TickQuery)) with type ChildF ListSlot ListQuery"

Any help would be really appreciated, thanks!


Solution

  • I looked at the types closer and saw that the second argument to peekList is a Coproduct wrapping an Either where the Left value is the list query that I want to peek. So just pattern match on those and add peekList to the component's peek parameter. Also I had to change the type signature to use ListQueryP instead of ListQuery.

      peekList :: forall a. H.ChildF ListSlot ListQueryP a -> H.ParentDSL State (ListStateP g) Query ListQueryP g ListSlot Unit
      peekList (H.ChildF _ (Coproduct queryEi)) =
        case queryEi of
          Left (AddTicker a) -> pure unit
          _ -> pure unit