MTL vs Transformers. Any status update?

Edward Kmett ekmett at
Mon Nov 30 20:02:15 EST 2009

On Mon, Nov 30, 2009 at 6:50 PM, Ross Paterson <ross at> wrote:

> On Sun, Nov 29, 2009 at 07:29:47PM -0500, Edward Kmett wrote:
> > The final issue is whether or not it is a good idea to eliminate the
> > simpler non-transformer versions of the monads.
> >
> > Without them, libraries that provide instances for the various monads
> > cannot provide instances for State and StateT in a way that lets them
> > work compatibly with both versions.
> >
> > So, an issue that I would like to talk about separately is if we
> > _should_ be dropping the basic State, Reader, Writer, etc. constructors.
> > They have definite pedagogical value, and have easier to understand
> > behavior for introductory purposes.  If we kept those then ALL code
> > that worked with mtl 1.2 would be compatible with mtl 2, which strikes
> > me as a desirable property.  This has the benefit that it is easier
> > to write libraries that export instances.  I think we would be remiss
> > in not at least considering the issue.  On the other hand, I don't
> > know how many libraries provide instances for the monads in the MTL.
> > I have a few in my monoids library, but I'd be willing to go either way.
> The benefit of defining these as type synonyms is that the Haskell 98
> transformers package has the same functions operating on both the base
> monad and the corresponding transformer; there is no need to define two
> versions of everything.  Similarly fewer instances are required in the
> monad class packages.

True. Like I said, I'd be happy with either way.

> I think the pedagogical issue can be handled in other ways, and that
> making compatibility with the current mtl an overriding requirement
> would be unduly constraining.  In any case there would be no complete
> compatibility, as transformers adds Applicative and Alternative instances,
> and also changes the constraints on Functor instances.

I agree that perfect backwards compatibility is impossible. That said,
unlike the type aliases, these are all cases where something new would work
that didn't previously. Library code that wanted to be backwards compatible
could avoid using the new instances, and the more permissive Functor
instances shouldn't break any code that worked before unless that code was
defining its own local version of Applicative, Alternative, etc. which were
constrained by the restrictive Functor definitions to not work in the most
permissive form anyway, so where needed, library code could work around
using WrappedMonad, etc. in a way that would be compatible.

It is true, that it would constrain the design of the mtl to carry a handful
of handy (or burdensome, depending on your perspective) tutorial
constructors around, but note that the functions themselves for working with
the simpler type are still contained in transformers, so the function count
doesn't really change either way. But the other way says that all of the
libraries that re-export functionality on top of the mtl must discard
coverage of the non-transformer case when linked against the old mtl.

Both options suck, but only one provides no way out except to force someone
up to the new version that they may not be able to use because of other
package requirements. I have yet to see any major migration to a new version
of a library that isn't more or less plug in compatible with the old version
actually take hold (witness current adoption levels of parsec 3 & quickcheck

I hope this doesn't across as too cynical. I just figured that someone
should play devil's advocate, before things got drowned in a sea of +1s.

-Edward Kmett

> Libraries mailing list
> Libraries at
-------------- next part --------------
An HTML attachment was scrubbed...

More information about the Libraries mailing list