
The easiest thing to do is just build your code with cabal, which will
ensure you're using consistent versions. (Similar questions came up
twice recently on Stack Overflow[1][2].) Wiping our your ~/.ghc and
installing from scratch should work also, but it's like using a
tactical nuke instead of a scalpel.
As for checking versions of dependencies, try `ghc-pkg describe conduit`.
Michael
[1] http://stackoverflow.com/questions/10729291/lifting-trouble-with-resourcet/1...
[2] http://stackoverflow.com/questions/10843547/snap-monad-liftio-and-ghc-7-4-1/...
On Sun, Jun 3, 2012 at 3:01 AM, Myles C. Maxfield
It could be. Do you know how I can check which versions of packages other packages have built against with Cabal? Will it help if I remove all the relevant packages and then re-install only a single version?
Thanks, Myles
On Saturday, June 2, 2012, Antoine Latter wrote:
Is it possible that you are puuling in two different versions of the package that defines the MonadThrow class?
That is, package a was built against version 1, but package b was built against version 2? This would make GHC think the type-class were incompatable.
This is just a guess - I have not tried what you are trying.
On Jun 2, 2012 6:35 PM, "Myles C. Maxfield"
wrote: To: Michael Snoyman CC: haskell-cafe
Hello, I'm having a problem working with the conduit library, and was hoping you could help me out.
Data.Conduit re-exports ResourceT, MonadResource, and MonadThrow (but not ExceptionT) from Control.Monad.Trans.Resource. I have a conduit which operates on a monad in the MonadThrow class. I am trying to figure out which MonadThrow class this should be (the Data.Conduit.MonadThrow class, or the Montrol.Monad.Trans.Resource.MonadThrow class, since apparently GHC doesn't recognize them as the same, even though one is just a re-export of the other).
If a user of this conduit wants to chain this conduit up with something like sourceFile, the underlying monad has to be a member of Data.Conduit.MonadResource and whatever MonadThrow class I chose to use. I would like to be able to use an existing instance to lift the class of the inner monad to the class of the entire monad stack (so I don't have to tell the user of my conduit that they have to define their own instances), and the only rule that I can find that does that is the following from Data.Conduit:
Data.Conduit.MonadThrow m => Data.Conduit.MonadThrow (Data.Conduit.ResourceT m)
However, GHC doesn't seem to think that Control.Monad.Trans.Resource.ExceptionT is an instance of Data.Conduit.MonadThrow:
No instance for (Data.Conduit.MonadThrow (ExceptionT IO)) arising from a use of `.....'
Control.Monad.Trans.Resource has a similar instance:
Control.Monad.Trans.Resource.MonadThrow m => Control.Monad.Trans.Resource.MonadThrow (Control.Monad.Trans.Resource.ResourceT m)
but because sourceFile operates in the Data.Conduit.MonadResource class, and Control.Monad.Trans.Resource.ResourceT isn't a member of that class (it's only a member of Control.Monad.Trans.Resource.MonadResource), that doesn't help:
No instance for (Data.Conduit.MonadResource (Control.Monad.Trans.Resource.ResourceT (ExceptionT IO))) arising from a use of `.....'
It should be noted that neither module defines anything like the following:
MonadResource m => MonadResource (ExceptionT m)
It seems like the underlying problem here is that: 1) I am required to use the Control.Monad.Trans.Resource.ExceptionT class, because Data.Conduit doesn't re-export it 2) I am required to use the Data.Conduit.MonadResource class, because sourceFile and others require it 3) There doesn't seem to be an existing instance that bridges between the two.
This seems like a fundamental flaw with re-exporting; it can only work if you re-export every single last thing from the original module. This doesn't seem tenable because the orignal module might not be under your control, so its author can add new symbols whenever he/she wants to.
I see two solutions to this problem: 1) Re-export Control.Monad.Trans.Resource.ExceptionT in Data.Conduit. This will work until someone adds something to the resourcet package and someone wants to use the new addition and Data.Conduit.ResourceT in the same stack 2) Don't re-export anything in Data.Conduit; make sourceFile and others explicitly depend on types in another module, but this might break compatibility with existing programs if they use fully-qualified symbol names. 3) Make anyone who wants to use a monad stack in MonadThrow and MonadResource define their own instances. This is probably no good because it means that many different modules will implement the same instance in potentially many different ways.
I feel like option 2) is probably the best solution here. I'm perfectly happy to issue a pull request for whichever option you think is best, but I don't know which solution you think is best for your project. What do you think?
--Myles
_______________________________________________ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://www.haskell.org/mailman/listinfo/haskell-cafe